需要更多帮助将CRC函数从VB.NET转换为C#

时间:2022-09-01 11:32:01

I probably should have just put all this in one question, sorry for that :(

我可能应该把所有这些都放在一个问题中,抱歉:(

Second error

Ok, this should be the end of errors (hopefully):

好的,这应该是错误的结束(希望如此):

private static string getCRC(string input, bool appendDate)
{
    string toEnc = string.Format("{0}{1}", input, appendDate == true ? string.Format("{0:yyyyMMdd}", System.DateTime.Now) : "");
    System.IO.MemoryStream mStream = new System.IO.MemoryStream(System.Text.ASCIIEncoding.ASCII.GetBytes(toEnc), false);

    CRC32 oCRC = new CRC32();
    return oCRC.GetCrc32(((System.IO.Stream)mStream)).ToString();
}

Error is on the return line:

错误在返回行:

Compiler Error Message: CS1502: The best overloaded method match for 'CRC.CRC32.GetCrc32(ref System.IO.Stream)' has some invalid arguments

编译器错误消息:CS1502:'CRC.CRC32.GetCrc32(ref System.IO.Stream)'的最佳重载方法匹配有一些无效的参数

Here is the function it is referring to:

这是它所指的功能:

public UInt32 GetCrc32(ref System.IO.Stream stream)
{
    //Dim crc32Result As Integer = &HFFFFFFFF
    UInt32 crc32Result = UInt32.MaxValue;

    try
    {

        byte[] buffer = new byte[BUFFER_SIZE];
        int readSize = BUFFER_SIZE;

        int count = stream.Read(buffer, 0, readSize);
        int i;
        UInt32 iLookup;
        //Dim tot As Integer = 0
        while ((count > 0))
        {
            for (i = 0; i <= count - 1; i++)
            {
                iLookup = (crc32Result & 0xff) ^ buffer[i];
                //crc32Result = ((crc32Result And &HFFFFFF00) \ &H100) And &HFFFFFF                     ' nasty shr 8 with vb :/
                crc32Result = ((UInt32)((crc32Result & 4294967040L) / 256) & UInt32.MaxValue);
                // nasty shr 8 with vb :/
                crc32Result = crc32Result ^ crc32Table[iLookup];
            }
            count = stream.Read(buffer, 0, readSize);
        }
    }
    catch (Exception ex)
    {
        HttpContext.Current.Response.Output.Write(string.Format("{0}{1}{2}", ex.Message, Environment.NewLine, ex.StackTrace));
        System.Diagnostics.Debugger.Break();
    }

    return (~crc32Result);

}

As you can see I tried to cast the memorystream as a stream, but I don't think it liked that too much.

正如你所看到的,我试图将内存流作为一个流进行转换,但我认为它不太喜欢它。

First error

(solved here)

If you have not seen my last couple of questions, I have a CRC function written in VB.NET. I used an online converter to convert it over to C#. Here is the original VB code:

如果你还没有看到我的最后几个问题,我有一个用VB.NET编写的CRC函数。我使用在线转换器将其转换为C#。这是原始的VB代码:

Public Sub New()
    Dim dwPolynomial As UInt32 = 3988292384
    Dim i As Integer, j As Integer

    ReDim crc32Table(256)
    Dim dwCrc As UInt32

    For i = 0 To 255
        dwCrc = i
        For j = 8 To 1 Step -1
            If (dwCrc And 1) Then
                dwCrc = ((dwCrc And &HFFFFFFFE) \ 2&) And &H7FFFFFFF
                dwCrc = dwCrc Xor dwPolynomial
            Else
                dwCrc = ((dwCrc And &HFFFFFFFE) \ 2&) And &H7FFFFFFF
            End If
        Next j
        crc32Table(i) = dwCrc
    Next i
End Sub

Here is my converted code. I fixed a few of the errors I was having but there are few more that I cannot figure out:

这是我转换的代码。我解决了我遇到的一些错误,但还有一些我无法弄清楚:

public CRC32()
{
    UInt32 dwPolynomial = ((UInt32)3988292384L);
    int i;
    int j;

    UInt32[] crc32Table;
    crc32Table = new UInt32[256];
    UInt32 dwCrc;

    for (i = 0; i <= 255; i++)
    {
        dwCrc = ((UInt32)i);
        for (j = 8; j >= 1; j -= 1)
        {
            if ((dwCrc & 1))
            {
                dwCrc = ((dwCrc & 0xfffffffe) / 2L) & 0x7fffffff;
                dwCrc = dwCrc ^ dwPolynomial;
            }
            else
            {
                dwCrc = ((dwCrc & 0xfffffffe) / 2L) & 0x7fffffff;
            }
        }
        crc32Table[i] = dwCrc;
    }
}

The first error is on this line:

第一个错误是在这一行:

Compiler Error Message: CS0030: Cannot convert type 'uint' to 'bool'

编译器错误消息:CS0030:无法将类型'uint'转换为'bool'

if ((dwCrc & 1))

if((dwCrc&1))

Should I be comparing these two values with a different operator? I am not too sure about why the & operator is there to be honest.

我应该将这两个值与不同的运算符进行比较吗?我不太清楚为什么&运营商诚实。

Thanks SO.

6 个解决方案

#1


There's no implicit integer-to-boolean conversion in C#. You have to compare against 0 explicity:

C#中没有隐式的整数到布尔转换。你必须比较0明显:

if ((dwCrc & 1) != 0) ...

#2


C# do not assume that 0 is equal false, and that 1 is equal true.

C#不假设0等于false,并且1等于true。

Thus

if ((dwCrc & 1) == 1) { }

Would be what you need.

将是你需要的。

#3


For your 2nd problem (which would have gotten more traffic if you posted it as a 2nd question):

对于你的第二个问题(如果你把它作为第二个问题发布会增加流量):

The best overloaded method match for 'CRC.CRC32.GetCrc32(ref System.IO.Stream)' has some invalid arguments

'CRC.CRC32.GetCrc32(ref System.IO.Stream)'的最佳重载方法匹配有一些无效的参数

Remove the ref modifier on the C# code:

删除C#代码上的ref修饰符:

public UInt32 GetCrc32(ref System.IO.Stream stream)

becomes

public UInt32 GetCrc32(System.IO.Stream stream)

I suspect the original VB.NET had ByRef where it wasn't necessary - I don't see you reassigning the value of stream anywhere.

我怀疑最初的VB.NET有没有必要的ByRef - 我没有看到你在任何地方重新分配流的价值。

Alternatively, call it with a ref parameter:

或者,使用ref参数调用它:

return oCRC.GetCrc32(ref mStream).ToString();

#4


With the help of ReSharper I got your converted code to compile.

在ReSharper的帮助下,我得到了转换后的代码进行编译。

Try this out:

试试这个:

    public void CRC32()
    {
        UInt32 dwPolynomial = ((UInt32) 3988292384L);
        int i;
        int j;

        UInt32[] crc32Table;
        crc32Table = new UInt32[256];
        UInt32 dwCrc;

        for (i = 0; i <= 255; i++)
        {
            dwCrc = ((UInt32) i);
            for (j = 8; j >= 1; j -= 1)
            {
                if ((dwCrc & 1) != 0u)
                {
                    dwCrc = (uint) (((dwCrc & 0xfffffffe)/2L) & 0x7fffffff);
                    dwCrc = dwCrc ^ dwPolynomial;
                }
                else
                {
                    dwCrc = (uint) (((dwCrc & 0xfffffffe)/2L) & 0x7fffffff);
                }
            }

            crc32Table[i] = dwCrc;
        }
    }

#5


That particular line is bitwise-ANDing dwCrc and 1, which is just 0x01. So basically, it's checking that dwCrc's least significant bit is a 1, not a 0. If it is, the result will be 1. If not, the result is 0. In VB, integers are converted to bools automatically (0 -> false, everything else -> true). In C#, you have to compare it with a value explicitly

该特定行是按位AND运算dwCrc和1,它只是0x01。所以基本上,它检查dwCrc的最低有效位是1,而不是0.如果是,结果将为1.如果不是,结果为0.在VB中,整数自动转换为bools(0 - > false ,其他一切 - >真实)。在C#中,您必须明确地将其与值进行比较

if ((dwCrc & 1) != 0) ...

(Also note that the ( & 1) is presumably needed, since it is checking for only one particular bit. If dwCrc == 0x02, then the original test will fail, as will the converted one. So doing something like

(另请注意,大概需要(&1),因为它只检查一个特定的位。如果dwCrc == 0x02,那么原始测试将失败,转换后的那个也会失败。所以做类似的事情

if(dwCrc != 0) ...

would be wrong, although it may not seem so at first.)

这可能是错的,虽然起初看起来可能不是这样。)

#6


Looks like a lot of these responses address your first error. The problem with your second error is that your GetCrc method expects the stream to be passed by reference (the ref keyword).

看起来很多这些响应都解决了您的第一个错误。您的第二个错误的问题是您的GetCrc方法期望通过引用传递流(ref关键字)。

In C#, If the method defines a parameter by reference, you have to explicitly pass it by reference when you call it. So add the ref keyword when you call your GetCrcMethod:

在C#中,如果方法通过引用定义参数,则在调用它时必须通过引用显式传递它。因此,在调用GetCrcMethod时添加ref关键字:

(also, you don't need the cast -- MemoryStream inherits from Stream)

(另外,你不需要强制转换 - MemoryStream继承自Stream)

return oCrc.GetCrc32(ref mStream).ToString();

One other consideration: Unless you plan to change which strem mStream references, you don't need to make a byRef parameter. Unless you plan to assign a value to stream (stream = new stream, or stream = null), it is more correct to just remove the ref keyword from the method declaration altogether.

另一个考虑因素:除非您计划更改哪个strem mStream引用,否则不需要创建byRef参数。除非您计划为stream(stream = new stream或stream = null)赋值,否则从方法声明中完全删除ref关键字更为正确。

#1


There's no implicit integer-to-boolean conversion in C#. You have to compare against 0 explicity:

C#中没有隐式的整数到布尔转换。你必须比较0明显:

if ((dwCrc & 1) != 0) ...

#2


C# do not assume that 0 is equal false, and that 1 is equal true.

C#不假设0等于false,并且1等于true。

Thus

if ((dwCrc & 1) == 1) { }

Would be what you need.

将是你需要的。

#3


For your 2nd problem (which would have gotten more traffic if you posted it as a 2nd question):

对于你的第二个问题(如果你把它作为第二个问题发布会增加流量):

The best overloaded method match for 'CRC.CRC32.GetCrc32(ref System.IO.Stream)' has some invalid arguments

'CRC.CRC32.GetCrc32(ref System.IO.Stream)'的最佳重载方法匹配有一些无效的参数

Remove the ref modifier on the C# code:

删除C#代码上的ref修饰符:

public UInt32 GetCrc32(ref System.IO.Stream stream)

becomes

public UInt32 GetCrc32(System.IO.Stream stream)

I suspect the original VB.NET had ByRef where it wasn't necessary - I don't see you reassigning the value of stream anywhere.

我怀疑最初的VB.NET有没有必要的ByRef - 我没有看到你在任何地方重新分配流的价值。

Alternatively, call it with a ref parameter:

或者,使用ref参数调用它:

return oCRC.GetCrc32(ref mStream).ToString();

#4


With the help of ReSharper I got your converted code to compile.

在ReSharper的帮助下,我得到了转换后的代码进行编译。

Try this out:

试试这个:

    public void CRC32()
    {
        UInt32 dwPolynomial = ((UInt32) 3988292384L);
        int i;
        int j;

        UInt32[] crc32Table;
        crc32Table = new UInt32[256];
        UInt32 dwCrc;

        for (i = 0; i <= 255; i++)
        {
            dwCrc = ((UInt32) i);
            for (j = 8; j >= 1; j -= 1)
            {
                if ((dwCrc & 1) != 0u)
                {
                    dwCrc = (uint) (((dwCrc & 0xfffffffe)/2L) & 0x7fffffff);
                    dwCrc = dwCrc ^ dwPolynomial;
                }
                else
                {
                    dwCrc = (uint) (((dwCrc & 0xfffffffe)/2L) & 0x7fffffff);
                }
            }

            crc32Table[i] = dwCrc;
        }
    }

#5


That particular line is bitwise-ANDing dwCrc and 1, which is just 0x01. So basically, it's checking that dwCrc's least significant bit is a 1, not a 0. If it is, the result will be 1. If not, the result is 0. In VB, integers are converted to bools automatically (0 -> false, everything else -> true). In C#, you have to compare it with a value explicitly

该特定行是按位AND运算dwCrc和1,它只是0x01。所以基本上,它检查dwCrc的最低有效位是1,而不是0.如果是,结果将为1.如果不是,结果为0.在VB中,整数自动转换为bools(0 - > false ,其他一切 - >真实)。在C#中,您必须明确地将其与值进行比较

if ((dwCrc & 1) != 0) ...

(Also note that the ( & 1) is presumably needed, since it is checking for only one particular bit. If dwCrc == 0x02, then the original test will fail, as will the converted one. So doing something like

(另请注意,大概需要(&1),因为它只检查一个特定的位。如果dwCrc == 0x02,那么原始测试将失败,转换后的那个也会失败。所以做类似的事情

if(dwCrc != 0) ...

would be wrong, although it may not seem so at first.)

这可能是错的,虽然起初看起来可能不是这样。)

#6


Looks like a lot of these responses address your first error. The problem with your second error is that your GetCrc method expects the stream to be passed by reference (the ref keyword).

看起来很多这些响应都解决了您的第一个错误。您的第二个错误的问题是您的GetCrc方法期望通过引用传递流(ref关键字)。

In C#, If the method defines a parameter by reference, you have to explicitly pass it by reference when you call it. So add the ref keyword when you call your GetCrcMethod:

在C#中,如果方法通过引用定义参数,则在调用它时必须通过引用显式传递它。因此,在调用GetCrcMethod时添加ref关键字:

(also, you don't need the cast -- MemoryStream inherits from Stream)

(另外,你不需要强制转换 - MemoryStream继承自Stream)

return oCrc.GetCrc32(ref mStream).ToString();

One other consideration: Unless you plan to change which strem mStream references, you don't need to make a byRef parameter. Unless you plan to assign a value to stream (stream = new stream, or stream = null), it is more correct to just remove the ref keyword from the method declaration altogether.

另一个考虑因素:除非您计划更改哪个strem mStream引用,否则不需要创建byRef参数。除非您计划为stream(stream = new stream或stream = null)赋值,否则从方法声明中完全删除ref关键字更为正确。