为了更好地学习 vb.net 和 C#,我正在进行一个项目(在 SourceForge 上找到 TreeViewAdv)并尝试将其代码转换为 VB。虽然我希望能够手动转换代码(因为这是一个学习项目),但我目前正在使用 C# 到 VB 代码转换器(在 www.DeveloperFusion.com 上找到)来让球滚动和一些先基本了解。我转换的代码大部分没有问题,但有一个问题(可能是 2 个)。见代码:
C#
using System;
using System.Collections.Generic;
using System.Text;
using System.Drawing;
using System.Runtime.InteropServices;
using System.Drawing.Imaging;
namespace Aga.Controls
{
public static class BitmapHelper
{
[StructLayout(LayoutKind.Sequential)]
private struct PixelData
{
public byte B;
public byte G;
public byte R;
public byte A;
}
public static void SetAlphaChanelValue(Bitmap image, byte value)
{
if (image == null)
throw new ArgumentNullException("image");
if (image.PixelFormat != PixelFormat.Format32bppArgb)
throw new ArgumentException("Wrong PixelFormat");
BitmapData bitmapData = image.LockBits(new Rectangle(0, 0, image.Width, image.Height),
ImageLockMode.ReadWrite, PixelFormat.Format32bppArgb);
unsafe
{
PixelData* pPixel = (PixelData*)bitmapData.Scan0;
for (int i = 0; i < bitmapData.Height; i++)
{
for (int j = 0; j < bitmapData.Width; j++)
{
pPixel->A = value;
pPixel++;
}
pPixel += bitmapData.Stride - (bitmapData.Width * 4);
}
}
image.UnlockBits(bitmapData);
}
}
}
VB.Net(转换后)
Imports System.Collections.Generic
Imports System.Text
Imports System.Drawing
Imports System.Runtime.InteropServices
Imports System.Drawing.Imaging
Namespace Aga.Controls
Public NotInheritable Class BitmapHelper
Private Sub New()
End Sub
<StructLayout(LayoutKind.Sequential)> _
Private Structure PixelData
Public B As Byte
Public G As Byte
Public R As Byte
Public A As Byte
End Structure
Public Shared Sub SetAlphaChanelValue(ByVal image As Bitmap, ByVal value As Byte)
If image Is Nothing Then
Throw New ArgumentNullException("image")
End If
If image.PixelFormat <> PixelFormat.Format32bppArgb Then
Throw New ArgumentException("Wrong PixelFormat")
End If
Dim bitmapData As BitmapData = image.LockBits(New Rectangle(0, 0, image.Width, image.Height), ImageLockMode.ReadWrite, PixelFormat.Format32bppArgb)
Dim pPixel As Pointer(Of PixelData) = DirectCast(bitmapData.Scan0, Pointer(Of PixelData))
For i As Integer = 0 To bitmapData.Height - 1
For j As Integer = 0 To bitmapData.Width - 1
pPixel.A = value
pPixel += 1
Next
pPixel += bitmapData.Stride - (bitmapData.Width * 4)
Next
image.UnlockBits(bitmapData)
End Sub
End Class
End Namespace
我相信,问题中的代码行是: C#
PixelData* pPixel = (PixelData*)bitmapData.Scan0;
在VB中转换为这个
Dim pPixel As Pointer(Of PixelData) = DirectCast(bitmapData.Scan0, Pointer(Of PixelData))
Intellisense 告诉我Pointer(Of PixelData)有问题
我的问题: 让上面的 VB 代码像 C# 代码一样运行的最佳方法是什么(结果不是方法),以及为什么解决方案有效(我希望了解其中的原因)?
回答或评论时应牢记的事项:
1) 我已经了解 CRL 或托管编程语言不使用指针
2) 我不是想在 vb.net 中找到一种使用指针或不安全代码的方法,我知道这是不可能的。
3) 我不打算放弃 VB,也不希望简单地将 C# 代码保存在单独的程序集中并从 VB 中引用它。我知道它有局限性,但这是一个学习项目,所以当我去面试时,他们问我,“你能在 VB 中做 X吗?” 我可以自信地说是的。
4)同样,这里最重要的不是我走哪条路,而是目的地。我知道通过 C# 到目的地的路更短,但我希望通过 VB。
对于加分,我期待声明
pPixel += 1
不能在 VB 端工作(因为 pPixel 是一个结构,见上文),但它在 C# 端构建得很好。为什么这(工作/不工作)在各自的语言中。这不是关于安全/不安全代码块的问题,就像代码实际运行并且由于不适当的转换/类型使用(int 1 --> struct pPixel)而不会引发错误时一样,为什么?