none
詢問一段C#代碼轉VB.net 涉及指標的轉換問題 RRS feed

  • 問題

  • 各位大大好 小弟從網路上找到一段代碼

      Image<Bgr, Byte> image = new Image<Bgr, Byte>(@"指定路徑");
                MIplImage MIpImg = (MIplImage)System.Runtime.InteropServices.Marshal.PtrToStructure(image.Ptr, typeof(MIplImage));
                int imageHeight = MIpImg.height;
                int imageWidth = MIpImg.width;
                unsafe
                {
                    byte* npixel = (byte*)MIpImg.imageData;
                    for (int height = 0; height < imageHeight; height++)
                    {
                        for (int width = 0; width < imageWidth; width++)
                        {
                            npixel[0] = 255;  //blue
                            npixel[1] = 255;  //green
                            npixel[2] = 255;  //red
                            npixel += 3;
                        }
                    }

    上面的代碼牽扯到了指標  我想把它轉成VB.net的code 但是貼到自動轉換代碼的網站

    一碰到指標那邊就沒轍了 所以想跟各位大大詢問一下像上面這段代碼 涉及指標的話

    要怎麼改寫呢?

    以下是小弟自己試著改寫的代碼 不過好像不太對 XD

        Dim image As New Image(Of Bgr, [Byte])("指定路徑")
            Dim MIpImg As MIplImage = DirectCast(System.Runtime.InteropServices.Marshal.PtrToStructure(image.Ptr, GetType(MIplImage)), MIplImage)
            '*********************************************
            Dim c As Integer = 0
            '*******************
       
            Dim npixel As Object = CType(MIpImg.imageData, IntPtr)
            '*******************
           
    
            For height As Integer = 0 To image.Height - 1
                For width As Integer = 0 To image.Width - 1
                    npixel(0) = 255
                    'blue
                    npixel(1) = 255
                    'green
                    npixel(2) = 255
                    'red
                    npixel += 3
                Next
            Next



    • 已編輯 向恩 2013年9月12日 上午 08:12
    2013年9月12日 上午 08:11

解答

所有回覆

  • VB.NET 沒有指標的語法。

    http://stackoverflow.com/questions/5915874/how-can-i-use-unsafe-code-in-vb-net


    強力監督SQL Injection問題!!

      • 小朱的技術隨手寫:http://www.dotblogs.com.tw/regionbbs/
      • 雲端學堂Facebook: http://www.facebook.com/studyazure


    2013年9月12日 上午 08:54
    版主
  • 沒有指標的語法 ?  所以小朱大大您的意思是牽扯到指標的 .net 庫

    在C#可使用 但在VB.net沒有變通的做法嗎? 

    事實上這個範例 用的是emgucv 這個.net的dll 呼叫出來的應用

    原始範例也是用C#寫的 問題是這段代碼沒法改寫成VB.net的形式嗎?

    2013年9月13日 上午 04:07
  • C# 有 unsafe 可操作指標,VB 沒有。

    最好的方式是用 C# 把 unsafe 的作業包起來寫成共用的類別庫,再由 VB 去呼叫它。


    強力監督SQL Injection問題!!

      • 小朱的技術隨手寫:http://www.dotblogs.com.tw/regionbbs/
      • 雲端學堂Facebook: http://www.facebook.com/studyazure

    2013年9月13日 上午 04:20
    版主
  • 在 VBNET 是利用 Buffer.BlockCopy 拷貝到陣列處理完畢後再拷貝回去。

    不精確的問法,就會得到隨便猜的答案;自己都不肯花時間好好描述問題,又何必期望網友會認真回答?

    2013年9月13日 下午 01:18
  • 心冷大大 聽你的意思 你的做法還是可以處理沒有指標的程式 但是這裡有個我很納悶的問題

     byte* npixel = (byte*)MIpImg.imageData;

    C# 這行好像是可以用指標指到陣列的位置  但vb的話這邊只能寫到指定到指標位置

    Dim npixel AsIntptr= MIpImg.imageData

    那取到這個指標後的陣列怎麼取呢?  我以為我宣告的MIpImg 這個變數所調用的庫 有直接返回陣列的方法

    但找了一下好像沒有這個類似的東西  這樣你說的方法要怎麼實現阿?


    • 已編輯 向恩 2013年9月14日 上午 07:51
    2013年9月14日 上午 07:51
  • 既有討論,關鍵字為 LockBits

    http://social.msdn.microsoft.com/Forums/zh-TW/home?forum=232#forum=232&sort=relevancedesc&brandIgnore=True&searchTerm=LockBits&content=Search


    不精確的問法,就會得到隨便猜的答案;自己都不肯花時間好好描述問題,又何必期望網友會認真回答?

    • 已標示為解答 向恩 2013年9月16日 下午 11:41
    2013年9月15日 上午 03:45
  • 樓主,

    如果你需要使用unsafe進行操作,可以用C#封裝成一個類庫,在VB.NET中直接引用。


    If you think one reply solves your problem, please mark it as An Answer, if you think someone's reply helps you, please mark it as a Proposed Answer

    Help by clicking:
    Click here to donate your rice to the poor
    Click to Donate
    Click to feed Dogs & Cats


    Found any spamming-senders? Please report at: Spam Report

    2013年9月15日 上午 03:55
  • 既有討論,關鍵字為 LockBits

    http://social.msdn.microsoft.com/Forums/zh-TW/home?forum=232#forum=232&sort=relevancedesc&brandIgnore=True&searchTerm=LockBits&content=Search


    不精確的問法,就會得到隨便猜的答案;自己都不肯花時間好好描述問題,又何必期望網友會認真回答?

    謝謝 心冷大大的提示 

    我搭配這章的做法:

    http://msdn.microsoft.com/en-gb/library/5ey6h79d.aspx

         

    然後再搭配 imagesize這個函式 它可以返回影像的佔據的資料位元數 去宣告byte陣列 就可以達成了

    以下是code:

     Dim image As New Image(Of Bgr, [Byte])("圖像路徑")
            Dim MIpImg As MIplImage = DirectCast(System.Runtime.InteropServices.Marshal.PtrToStructure(image.Ptr, GetType(MIplImage)), MIplImage)
            '*********************************************
    
            '*******************
    
            Dim npixel As IntPtr = MIpImg.imageData
    
            Dim bytes As Integer = MIpImg.imageSize
    
            Dim rgbValues(bytes - 1) As Byte
    
            System.Runtime.InteropServices.Marshal.Copy(npixel, rgbValues, 0, bytes)
    
            '*******************
            'For counter As Integer = 2 To rgbValues.Length - 1 Step 3
            For counter As Integer = 0 To rgbValues.Length - 1 Step 3
                rgbValues(counter) = 0   'blue
                rgbValues(counter + 1) = 0    'green
                rgbValues(counter + 2) = 0    'red
            Next
    
    
            System.Runtime.InteropServices.Marshal.Copy(rgbValues, 0, npixel, bytes)
    
            Me.PictureBox1.Image = image.Bitmap




    • 已編輯 向恩 2013年9月16日 下午 11:41
    2013年9月16日 下午 11:40
  • 要注意的是原圖的格式。

    全彩 32/24 bits 分別對應到 4 / 3 bytes 。

    可以透過 New Bitmap 指定彩度後,使用 DrawImage 轉移。

    比如說你的 圖像路徑 指到 32 bits 彩度檔案,則你的程式碼會有問題。


    不精確的問法,就會得到隨便猜的答案;自己都不肯花時間好好描述問題,又何必期望網友會認真回答?

    2013年9月17日 下午 12:53
  • 其實好像不用用New Bitmap 去指定彩度  emgucv 這個庫它好像提供設計者可以去宣告要使用rgb

    還是要用rgba來取得圖的資料結構 我只要在宣告Image 的時候 去定義好就好了

    2013年9月17日 下午 03:39
  • 以下是code:

             For counter As Integer = 0 To rgbValues.Length - 1 Step 3
                rgbValues(counter) = 0   'blue
                rgbValues(counter + 1) = 0    'green
                rgbValues(counter + 2) = 0    'red
            Next
    
    

    我是針對這段提出色深要注意的問題。

    不精確的問法,就會得到隨便猜的答案;自己都不肯花時間好好描述問題,又何必期望網友會認真回答?

    2013年9月18日 下午 12:22
  • 以下是code:

             For counter As Integer = 0 To rgbValues.Length - 1 Step 3
                rgbValues(counter) = 0   'blue
                rgbValues(counter + 1) = 0    'green
                rgbValues(counter + 2) = 0    'red
            Next
    

    我是針對這段提出色深要注意的問題。

    不精確的問法,就會得到隨便猜的答案;自己都不肯花時間好好描述問題,又何必期望網友會認真回答?

    色深不是宣告Bgra的資料結構後 然後才在迴圈裡處理 Alpha的資料就好了

    如下:

    For counter As Integer = 0 To rgbValues.Length - 1 Step 3 rgbValues(counter) = 0 'blue rgbValues(counter + 1) = 0 'green rgbValues(counter + 2) = 0 'red

    rgbValues(counter + 3) = 0 'Alpha

    Next

    2013年9月18日 下午 02:08
  • 色深是你圖檔決定的,所以程式碼中需要判斷圖檔原始色深,懶的判斷就是一律將圖檔轉換成 32 bits 色深,也就是配合 New Bitmap / DrawImage。


    不精確的問法,就會得到隨便猜的答案;自己都不肯花時間好好描述問題,又何必期望網友會認真回答?

    2013年9月19日 上午 09:42