天道酬勤,学无止境

C#中的CRC-ITU计算(CRC-ITU calculation in c#)

问题

我是 C# 的新手。 我需要计算从 GPS 设备收到的数据包的 CRC-ITU。 文档中提供了 C 代码,但我不知道如何将其移植到 C#,有人可以帮助我吗?

这是 C 中的 CRC-ITU 算法:

static const U16 crctab16[] = 
{
    0x0000, 0x1189, 0x2312, 0x329b, 0x4624, 0x57ad, 0x6536, 0x74bf,
    0x8c48, 0x9dc1, 0xaf5a, 0xbed3, 0xca6c, 0xdbe5, 0xe97e, 0xf8f7,
    0x1081, 0x0108, 0x3393, 0x221a, 0x56a5, 0x472c, 0x75b7, 0x643e,
    0x9cc9, 0x8d40, 0xbfdb, 0xae52, 0xdaed, 0xcb64, 0xf9ff, 0xe876,
    0x2102, 0x308b, 0x0210, 0x1399, 0x6726, 0x76af, 0x4434, 0x55bd,
    0xad4a, 0xbcc3, 0x8e58, 0x9fd1, 0xeb6e, 0xfae7, 0xc87c, 0xd9f5,
    0x3183, 0x200a, 0x1291, 0x0318, 0x77a7, 0x662e, 0x54b5, 0x453c,
    0xbdcb, 0xac42, 0x9ed9, 0x8f50, 0xfbef, 0xea66, 0xd8fd, 0xc974,
    0x4204, 0x538d, 0x6116, 0x709f, 0x0420, 0x15a9, 0x2732, 0x36bb,
    0xce4c, 0xdfc5, 0xed5e, 0xfcd7, 0x8868, 0x99e1, 0xab7a, 0xbaf3,
    0x5285, 0x430c, 0x7197, 0x601e, 0x14a1, 0x0528, 0x37b3, 0x263a,
    0xdecd, 0xcf44, 0xfddf, 0xec56, 0x98e9, 0x8960, 0xbbfb, 0xaa72,
    0x6306, 0x728f, 0x4014, 0x519d, 0x2522, 0x34ab, 0x0630, 0x17b9,
    0xef4e, 0xfec7, 0xcc5c, 0xddd5, 0xa96a, 0xb8e3, 0x8a78, 0x9bf1,
    0x7387, 0x620e, 0x5095, 0x411c, 0x35a3, 0x242a, 0x16b1, 0x0738,
    0xffcf, 0xee46, 0xdcdd, 0xcd54, 0xb9eb, 0xa862, 0x9af9, 0x8b70,
    0x8408, 0x9581, 0xa71a, 0xb693, 0xc22c, 0xd3a5, 0xe13e, 0xf0b7,
    0x0840, 0x19c9, 0x2b52, 0x3adb, 0x4e64, 0x5fed, 0x6d76, 0x7cff,
    0x9489, 0x8500, 0xb79b, 0xa612, 0xd2ad, 0xc324, 0xf1bf, 0xe036,
    0x18c1, 0x0948, 0x3bd3, 0x2a5a, 0x5ee5, 0x4f6c, 0x7df7, 0x6c7e,
    0xa50a, 0xb483, 0x8618, 0x9791, 0xe32e, 0xf2a7, 0xc03c, 0xd1b5,
    0x2942, 0x38cb, 0x0a50, 0x1bd9, 0x6f66, 0x7eef, 0x4c74, 0x5dfd,
    0xb58b, 0xa402, 0x9699, 0x8710, 0xf3af, 0xe226, 0xd0bd, 0xc134,
    0x39c3, 0x284a, 0x1ad1, 0x0b58, 0x7fe7, 0x6e6e, 0x5cf5, 0x4d7c,
    0xc60c, 0xd785, 0xe51e, 0xf497, 0x8028, 0x91a1, 0xa33a, 0xb2b3,
    0x4a44, 0x5bcd, 0x6956, 0x78df, 0x0c60, 0x1de9, 0x2f72, 0x3efb,
    0xd68d, 0xc704, 0xf59f, 0xe416, 0x90a9, 0x8120, 0xb3bb, 0xa232,
    0x5ac5, 0x4b4c, 0x79d7, 0x685e, 0x1ce1, 0x0d68, 0x3ff3, 0x2e7a,
    0xe70e, 0xf687, 0xc41c, 0xd595, 0xa12a, 0xb0a3, 0x8238, 0x93b1,
    0x6b46, 0x7acf, 0x4854, 0x59dd, 0x2d62, 0x3ceb, 0x0e70, 0x1ff9,
    0xf78f, 0xe606, 0xd49d, 0xc514, 0xb1ab, 0xa022, 0x92b9, 0x8330,
    0x7bc7, 0x6a4e, 0x58d5, 0x495c, 0x3de3, 0x2c6a, 0x1ef1, 0x0f78,
};

    // calculate 16 bits CRC of the given length data.
U16 GetCrc16(const U8* pData, int nLength)
{
U16 fcs = 0xffff; // Initialize

while(nLength>0){
fcs = (fcs >> 8) ^ crctab16[(fcs ^ *pData) & 0xff];
nLength--;
pData++;
}
return ~fcs; // Negate
}

// Check whether the 16 bits CRC of the given length data is right.
 BOOL IsCrc16Good(const U8* pData, int nLength)
{
    U16 fcs = 0xffff;    // Initialize
    while(nLength>0){
        fcs = (fcs >> 8) ^ crctab16[(fcs ^ *pData) & 0xff];
        nLength--;
        pData++;
    }
    return (fcs == 0xf0b8);  // 0xf0b8 is CRC-ITU的"Magic Value"
}

我还从 http://ppcode.blogbus.com/logs/1656947.html 找到了 C# 代码,但我不知道如何使用它,这是代码

public class CrcITUTable
 {
  static ushort [] crctab16 =
   {
    0x0000, 0x1189, 0x2312, 0x329b, 0x4624, 0x57ad, 0x6536, 0x74bf,
    0x8c48, 0x9dc1, 0xaf5a, 0xbed3, 0xca6c, 0xdbe5, 0xe97e, 0xf8f7,
    0x1081, 0x0108, 0x3393, 0x221a, 0x56a5, 0x472c, 0x75b7, 0x643e,
    0x9cc9, 0x8d40, 0xbfdb, 0xae52, 0xdaed, 0xcb64, 0xf9ff, 0xe876,
    0x2102, 0x308b, 0x0210, 0x1399, 0x6726, 0x76af, 0x4434, 0x55bd,
    0xad4a, 0xbcc3, 0x8e58, 0x9fd1, 0xeb6e, 0xfae7, 0xc87c, 0xd9f5,
    0x3183, 0x200a, 0x1291, 0x0318, 0x77a7, 0x662e, 0x54b5, 0x453c,
    0xbdcb, 0xac42, 0x9ed9, 0x8f50, 0xfbef, 0xea66, 0xd8fd, 0xc974,
    0x4204, 0x538d, 0x6116, 0x709f, 0x0420, 0x15a9, 0x2732, 0x36bb,
    0xce4c, 0xdfc5, 0xed5e, 0xfcd7, 0x8868, 0x99e1, 0xab7a, 0xbaf3,
    0x5285, 0x430c, 0x7197, 0x601e, 0x14a1, 0x0528, 0x37b3, 0x263a,
    0xdecd, 0xcf44, 0xfddf, 0xec56, 0x98e9, 0x8960, 0xbbfb, 0xaa72,
    0x6306, 0x728f, 0x4014, 0x519d, 0x2522, 0x34ab, 0x0630, 0x17b9,
    0xef4e, 0xfec7, 0xcc5c, 0xddd5, 0xa96a, 0xb8e3, 0x8a78, 0x9bf1,
    0x7387, 0x620e, 0x5095, 0x411c, 0x35a3, 0x242a, 0x16b1, 0x0738,
    0xffcf, 0xee46, 0xdcdd, 0xcd54, 0xb9eb, 0xa862, 0x9af9, 0x8b70,
    0x8408, 0x9581, 0xa71a, 0xb693, 0xc22c, 0xd3a5, 0xe13e, 0xf0b7,
    0x0840, 0x19c9, 0x2b52, 0x3adb, 0x4e64, 0x5fed, 0x6d76, 0x7cff,
    0x9489, 0x8500, 0xb79b, 0xa612, 0xd2ad, 0xc324, 0xf1bf, 0xe036,
    0x18c1, 0x0948, 0x3bd3, 0x2a5a, 0x5ee5, 0x4f6c, 0x7df7, 0x6c7e,
    0xa50a, 0xb483, 0x8618, 0x9791, 0xe32e, 0xf2a7, 0xc03c, 0xd1b5,
    0x2942, 0x38cb, 0x0a50, 0x1bd9, 0x6f66, 0x7eef, 0x4c74, 0x5dfd,
    0xb58b, 0xa402, 0x9699, 0x8710, 0xf3af, 0xe226, 0xd0bd, 0xc134,
    0x39c3, 0x284a, 0x1ad1, 0x0b58, 0x7fe7, 0x6e6e, 0x5cf5, 0x4d7c,
    0xc60c, 0xd785, 0xe51e, 0xf497, 0x8028, 0x91a1, 0xa33a, 0xb2b3,
    0x4a44, 0x5bcd, 0x6956, 0x78df, 0x0c60, 0x1de9, 0x2f72, 0x3efb,
    0xd68d, 0xc704, 0xf59f, 0xe416, 0x90a9, 0x8120, 0xb3bb, 0xa232,
    0x5ac5, 0x4b4c, 0x79d7, 0x685e, 0x1ce1, 0x0d68, 0x3ff3, 0x2e7a,
    0xe70e, 0xf687, 0xc41c, 0xd595, 0xa12a, 0xb0a3, 0x8238, 0x93b1,
    0x6b46, 0x7acf, 0x4854, 0x59dd, 0x2d62, 0x3ceb, 0x0e70, 0x1ff9,
    0xf78f, 0xe606, 0xd49d, 0xc514, 0xb1ab, 0xa022, 0x92b9, 0x8330,
    0x7bc7, 0x6a4e, 0x58d5, 0x495c, 0x3de3, 0x2c6a, 0x1ef1, 0x0f78,
   };

  public CrcITUTable()
  {
   //
   // TODO: 在此处添加构造函数逻辑
   //
  }

  unsafe public ushort GetCrcITU_T(byte * pData,int nLength,out string crcCode)
  {
   ushort fcs=0xFFFF;
   ushort uRlt;
   string strTmp;
   while(nLength>0)
   {
    fcs= (ushort) ((ushort)(fcs>>8)^ crctab16[(fcs ^ *pData) &0xFF ]);
    nLength--;
    pData++;
   }

   uRlt=(ushort)~fcs;
   strTmp=uRlt.ToString("X4") ;
   crcCode=strTmp.Substring(2,2) + " " + strTmp.Substring(0,2);

   return uRlt;
  }

  unsafe public bool IsCrcITUGood_T(byte * pData,int nLength)
  {
   ushort fcs=0xFFFF;
   while(nLength>0)
   {
    fcs= (ushort) ((ushort)(fcs>>8)^ crctab16[(fcs ^ *pData) &0xFF ]);
    nLength--;
    pData++;
   }

   return (fcs==0xF0B8);
  }

 }

这是文档中的一些示例:

完整数据包:0x78 0x78 0x0D 0x01 0x01 0x23 0x45 0x67 0x89 0x01 0x23 0x45 0x00 0x01 0x8C 0xDD 0x0D 0x0A

起始位:0x78 0x78 长度:0x0D 协议号:0x01 设备 ID:0x01 0x23 0x45 0x67 0x89 0x01 0x23 0x45 序列号:0x00 Bit 0x00xDD CRC 校验停止

引用自文档:

设备或服务器可以通过识别码判断接收到的数据的准确性。 有时,由于电子噪声或其他干扰,数据在传输过程中会发生一些变化。 在这种情况下,识别代码可以确保核心或关联核心对此类错误数据不做任何处理,从而增强系统的安全性和效率。 该识别码采用CRC-ITU识别方式。 CRC-ITU的值是协议中从“Package Length”到“Information Serial Number”(包括“Package Length”和“Information Serial Number”),如果接收方收到CRC计算错误的信息,则忽略并丢弃该数据包裹。

那么有人知道如何从上面的例子中获得 crc 值吗? 谢谢

回答1

只需按照文档的说明进行操作

CRC-ITU 值是从协议中的“Package Length”到“Information Serial Number”(包括“Package Length”和“Information Serial Number”)。

所以我们把数据从长度取到序列号

0x0D 0x01 0x01 0x23 0x45 0x67 0x89 0x01 0x23 0x45 0x00 0x01

现在我们使用这些数字集并将其传递给 CRC 函数。 您链接的代码使用了不安全的指针,我不知道您是否需要它们,因为您没有发布任何使用它的地方。 如果您有字节数组中的数据,您可以重新编写函数以仅传入字节数组而不是指针,那么代码将不再需要标记为不安全。

这是我使用字节的清理版本

static void Main(string[] args)
{
    byte[] dataPacket = { 0x78, 0x78, 0x0D, 0x01, 0x01, 0x23, 0x45, 0x67, 0x89, 0x01, 0x23, 0x45, 0x00, 0x01, 0x8C, 0xDD, 0x0D, 0x0A };
    var crc16 = GetCrc16(dataPacket, 2, 12);

    if (crc16 == ReadBigEndianUInt16(dataPacket, 14)))
    {
        Debugger.Break();
        //use packet.
    }

    Debugger.Break();
}

public static UInt16 ReadBigEndianUInt16(byte[] data, int offset)
{
    if(BitConverter.IsLittleEndian == true)
    {
        var bytes = new byte[2] {data[offset+1], data[offset]}            
        return BitConverter.ToUInt16(bytes, 0);
    }
    else
    {
         return BitConverter.ToUInt16(data, offset);
    }
}

public static ushort GetCrc16(byte[] data, int offset, int length)
{
    ushort fcs = 0xFFFF;
    for (int i = offset; i < length + offset; i++)
    {
        fcs = (ushort)((ushort)(fcs >> 8) ^ crctab16[(fcs ^ data[i]) & 0xFF]);
    }

    return (ushort)(~fcs);
}

public static bool IsCrcITUGood(byte[] data, int offset, int length)
{
    ushort fcs = 0xFFFF;
    for (int i = offset; i < length + offset; i++)
    {
        fcs = (ushort)((ushort)(fcs >> 8) ^ crctab16[(fcs ^ data[i]) & 0xFF]);
    }

    return (fcs == 0xF0B8); //magic value
}

static ushort[] crctab16 = /*(snip)*/;

看起来数据包中的 CRC 是以 big Endian 存储的,而 C# 代码会产生 little endian。 因此,在比较它们之前,您需要翻转 CRC 的两个字节。


作为旁注,我认为IsCrcITUGood方法不是来自 gps 规范。 我认为无论您从中提取此代码示例,都有一组特殊的字节使 CRC 始终等于0xF0B8 。 在您的数据中,它为您提供了预期的 CRC 值。 我找不到让 CRC 等于0xF0B8

回答2

发现很少有关于 CRC 16 计算的链接,但发现 javascript 中的 SO 答案之一很有帮助。

如果有人正在使用 python 寻找相同的 CRC 16 计算,请创建公共要点以及工作 python 小提琴示例:

https://gist.github.com/mrudang-vora/6a0767be085a275c0df3

希望它可以帮助某人。

标签

受限制的 HTML

  • 允许的HTML标签:<a href hreflang> <em> <strong> <cite> <blockquote cite> <code> <ul type> <ol start type> <li> <dl> <dt> <dd> <h2 id> <h3 id> <h4 id> <h5 id> <h6 id>
  • 自动断行和分段。
  • 网页和电子邮件地址自动转换为链接。

相关推荐
  • CRC-ITU calculation in c#
    I'm new to C#. I need to calculate CRC-ITU for the packet recieved from GPS devices. There is C code provided in the documentation but i don't know how to port it to C#, anyone could help me? here is CRC-ITU algorithm in C : static const U16 crctab16[] = { 0x0000, 0x1189, 0x2312, 0x329b, 0x4624, 0x57ad, 0x6536, 0x74bf, 0x8c48, 0x9dc1, 0xaf5a, 0xbed3, 0xca6c, 0xdbe5, 0xe97e, 0xf8f7, 0x1081, 0x0108, 0x3393, 0x221a, 0x56a5, 0x472c, 0x75b7, 0x643e, 0x9cc9, 0x8d40, 0xbfdb, 0xae52, 0xdaed, 0xcb64, 0xf9ff, 0xe876, 0x2102, 0x308b, 0x0210, 0x1399, 0x6726, 0x76af, 0x4434, 0x55bd, 0xad4a, 0xbcc3, 0x8e58
  • 16bit CRC-ITU calculation for Concox tracker
    I am creating C# code for a server program that receives data from a Concox TR06 GPS tracker via TCP: http://www.iconcox.com/uploads/soft/140920/1-140920023130.pdf When first starting up, the tracker sends a login message, which needs to be acknowledged before it will send any position data. My first problem is that, according to the documentation, the acknowledge message is 18 bytes long, yet the example they provide is only 10 bytes long: P.s. in the table above, the "bits" column I'm pretty sure should be labelled "bytes" instead... Now, my main problem is in calculating the Error Check
  • GPS Socket communication (CONCOX)
    1]1i have a gps device that should send GPRMC Data but it require login packect Review the dataSheet Device DataSheet i can recieve the login 787811010XXX739050313XXX20200001000E0EAD0D0A IMEI Sart With XXX the packet is different from the example Image i have 2 Questions 1-according to the data recieveid and the example what should i send 2- how to calcaulate the Error Check Thank You Edit public static void StartListening() { // Data buffer for incoming data. byte[] bytes = new Byte[1024]; // Establish the local endpoint for the socket. // The DNS name of the computer // running the listener
  • 计算 C# 中的代数表达式 [关闭](Calculate the algebraic expression in C# [closed])
    问题 关闭。 此问题不符合 Stack Overflow 准则。 它目前不接受答案。 想改善这个问题吗? 更新问题,使其成为 Stack Overflow 的主题。 7年前关闭。 改进这个问题 计算代数表达式 Z,其中 n 由用户输入。 使用2个for循环来解决问题。 到目前为止我的代码: using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Collections; namespace ConsoleApplication1 { class Program { static void Main(string[] args) { int n, k = 1; double z; float sum, p; n = Console.Read(); for (int i = 0; i < n; i+=2) { sum += p; for (int j = 0; j < n; j++) { p *= (3 * k + 2); } } } } } 我完全在 for 循环中......任何帮助表示赞赏。 回答1 p 必须初始化为 1 为 0 * X == 0 此外,i 和 j(为什么不是 k)必须初始化为 1
  • 为 CRC16 函数将 C 转换为 PHP(Convert C to PHP for CRC16 Function)
    问题 我需要帮助将 C 代码转换为 PHP。 以下是C代码: static const U16 crctab16[] = { 0x0000, 0x1189, ... }; U16 GetCrc16(const U8* pData, int nLength) { U16 fcs = 0xffff; while(nLength > 0) { fcs = (fcs >> 8) ^ crctab16[fcs ^ *pData) & 0xff]; nLength--; pData++; } return ~fcs; } 到目前为止,我已经成功转换了以下 PHP 代码: $crctab16 = array(0x0000, 0x1189, ... ); function getCrc16($pData) { $hexdata = pack('H*',$pData); $nLength = strlen($hexdata); $fcs = 0xFFFF; $pos = 0; while($nLength > 0) { $fcs = ($fcs >> 8) ^ $crctab16[($fcs ^ $hexdata[$pos]) & 0xFF]; $nLength--; $pos++; } return ~$fcs; } 我试图运行以下代码: $str = "0A1344010400010005"
  • C#:在 GPU 上执行操作,而不是 CPU(计算 Pi)[关闭](C#: Perform Operations on GPU, not CPU (Calculate Pi) [closed])
    问题 关闭。 此问题不符合 Stack Overflow 准则。 它目前不接受答案。 想改善这个问题吗? 更新问题,使其成为 Stack Overflow 的主题。 3年前关闭。 改进这个问题 我最近阅读了很多关于软件(主要是科学/数学和加密相关)的内容,这些软件将部分计算转移到 GPU 上,这导致支持操作的速度提高了 100-1000(!)倍。 是否有库、API 或其他方式可以通过 C# 在 GPU 上运行某些内容? 我正在考虑简单的 Pi 计算。 我有一个 GeForce 8800 GTX,如果这完全相关的话(不过我更喜欢独立于卡的解决方案)。 回答1 这是一项非常新的技术,但您可能会研究 CUDA。 由于您的问题是用 C# 标记的,因此这里是一个 .Net 包装器。 作为奖励,您的 8800 GTX 似乎支持 CUDA。 回答2 对于 C# 中的 GPU 计算,另一个未提及的选项是 Brahma。 Brahma 为 GPU 计算提供了一个基于 LINQ 的抽象——它基本上是 LINQ to GPU。 它无需额外的库即可在 OpenGL 和 DirectX 上运行(但需要 SM3)。 有些样品相当惊人。 回答3 你可能想看看这个问题 你可能正在寻找 Accelerator,但如果你对游戏开发感兴趣,我建议你看看 XNA 回答4 您可以使用 Windows API 代码包从
  • C# 只读计算属性,它们应该是方法吗?(C# read-only calculated properties, should they be methods?)
    问题 我有几个实体计算了它们的字段,例如 TotalCost。 现在我把它们都作为属性,但我想知道它们是否真的应该是方法。 是否有 C# 标准? public class WorkOrder { public int LaborHours { get; set; } public decimal LaborRate { get; set; } // Should this be LaborCost()? public decimal LaborCost { get { return LaborHours * LaborRate; } } } 回答1 使用计算属性而不是方法是可以的,只要计算不花费明显的时间 请参阅属性使用指南 回答2 我认为方法应该对对象执行操作,通常会更改对象的状态。 即使计算了属性,属性也应该反映对象的当前状态。 所以你应该保留你的财产 IMO。 回答3 我认为它们都应该是属性。 只要它不改变对象的状态,我就把它作为一个属性很酷。 此外,如果我使用您的类进行数据绑定(WPF 等),那么我可以直接绑定到您的属性,而无需修改/扩展该类。 回答4 如果它们 a) 轻量级且 b) 没有副作用,我会将它们设为属性。 轻量级当然有点模糊,但经验法则是:如果我不得不担心调用属性(无论是在循环中还是在其他任何地方),它应该是一个方法。 回答5 我会把它们作为财产。 但是没有
  • C#:在搜索/计算期间禁用按钮(C#: Disable button during search/calculation)
    问题 我有一个搜索对话框,我想在搜索过程中禁用搜索按钮。 这是当前代码,但该按钮未停用 看法: <Button Content="Search" Command="{Binding StartSearchCommand}" IsEnabled="{Binding IsNotSearching}" /> 视图模型: private bool _isNotSearching; public bool IsNotSearching { get { return _isNotSearching; } set { _isNotSearching = value; OnPropertyChanged("IsNotSearching"); } } private RelayCommand<object> _startSearchCommand; public ICommand StartSearchCommand { get { if (_startSearchCommand == null) _startSearchCommand = new RelayCommand<object>(p => ExecuteSearch()); return _startSearchCommand; } } private void ExecuteSearch() { IsNotSearching =
  • 在 C# 中计算素数的最快方法?(Fastest way to calculate primes in C#?)
    问题 我实际上对我的问题有一个答案,但它不是并行化的,所以我对改进算法的方法很感兴趣。 无论如何,它可能对某些人有用。 int Until = 20000000; BitArray PrimeBits = new BitArray(Until, true); /* * Sieve of Eratosthenes * PrimeBits is a simple BitArray where all bit is an integer * and we mark composite numbers as false */ PrimeBits.Set(0, false); // You don't actually need this, just PrimeBits.Set(1, false); // remindig you that 2 is the smallest prime for (int P = 2; P < (int)Math.Sqrt(Until) + 1; P++) if (PrimeBits.Get(P)) // These are going to be the multiples of P if it is a prime for (int PMultiply = P * 2; PMultiply < Until; PMultiply += P)
  • 如何在 C# 中计算 PI?(How do I calculate PI in C#?)
    问题 如何使用 C# 计算 PI 的值? 我在想这将是通过一个递归函数,如果是这样,它会是什么样子,是否有任何数学方程来支持它? 我对性能不是太挑剔,主要是从学习的角度如何去做。 回答1 如果你想要递归: PI = 2 * (1 + 1/3 * (1 + 2/5 * (1 + 3/7 * (...)))) 经过一些重写后,这将变成: PI = 2 * F(1); 与 F(i): double F (int i) { return 1 + i / (2.0 * i + 1) * F(i + 1); } 艾萨克牛顿(你之前可能听说过他;))想出了这个技巧。 请注意,我省略了结束条件,以保持简单。 在现实生活中,你有点需要一个。 回答2 如何使用: double pi = Math.PI; 如果您想要比这更好的精度,则需要使用算法系统和 Decimal 类型。 回答3 如果你仔细看看这个非常好的指南: 并行编程模式:使用 .NET Framework 4 理解和应用并行模式 你会在第 70 页找到这个可爱的实现(我这边有一些小改动): static decimal ParallelPartitionerPi(int steps) { decimal sum = 0.0; decimal step = 1.0 / (decimal)steps; object obj = new
  • 如何计算C#中两个日期之间的月份数(How can I calculate the numbers of month between two dates in C#)
    问题 我想知道如何计算两个日期之间的月份数。 有没有什么方法可以在 C# 中计算它? Eg1. Date1 = "2011/11/01" Date2 = "2012/02/01" Result. Numbers of Month =3 Eg2. Date1 = "2012/01/31" Date2 = "2012/02/01" Result. Numbers of Month =1 Eg3. Date1 = "2012/01/01" Date2 = "2012/02/28" Result. Numbers of Month =1 回答1 这将导致月份之间的差异: int months = (Date2.Year - Date1.Year) * 12 + Date2.Month - Date1.Month; 回答2 我的 Noda Time 项目为此提供了: LocalDate date1 = new LocalDate(2011, 11, 1); LocalDate date2 = new LocalDate(2012, 2, 1); Period period = Period.Between(date1, date2, PeriodUnits.Months); long months = period.Months; // 3 有关更多信息,请参阅算术项目文档。
  • C#中的CRC-4实现(CRC-4 implementation in C#)
    问题 我一直在网上搜索4位循环冗余校验(CRC-4-ITU)的C#实现,但是到目前为止,我一直没有成功。 有谁能给我CRC-4-ITU的参考实现? 如果存在标准多项式,最好使用标准多项式(我已经读过维基百科指向的规范为CRC4规范,而没有找到该多项式的定义)。 我也非常感谢某种测试套件或测试数据来验证CRC4实现。 谢谢! 回答1 维基百科上的“循环冗余校验”文章说,多项式为x ^ 4 + x +1。关于校验和的计算方式也有相当不错的描述。 这是CRC16的算法。 我知道这不是您要的,但是将其适应4位应该相对简单。 public ushort calculate(byte[] bytes) { int crc = 0xFFFF; // initial value // loop, calculating CRC for each byte of the string for (int byteIndex = 0; byteIndex < bytes.Length; byteIndex++) { ushort bit = 0x80; // initialize bit currently being tested for (int bitIndex = 0; bitIndex < 8; bitIndex++) { bool xorFlag = ((crc & 0x8000) ==
  • 在C#中计算重复日期的正确方法(Correct way to calculate recurring dates in C#)
    问题 在我的项目中,我需要计算重复事件的日期。 在开始时,我只有一个开始日期/时间以及该事件必须如何重复的信息: Every Day Every Week Every 2 Weeks Every 3 Weeks Every Month Every 2 Months ... 什么是正确的方法? 它应该在不同的时区和夏令时设置下正常工作。 我想我应该将天/周/月添加到本地DateTime中,然后将其转换为UTC。 但是我不确定。 如果我再增加几天会发生什么,这就是我们需要将时钟向前调整一小时的时间。 在这种情况下,该时间将不存在。 以下是我编写的代码,但是我不确定它在每种情况下均能正常工作: private static List<DateTime> FindOccurrences(DateTime localStart, Repeat repeat, int occurrences) { var result = new List<DateTime> { localStart }; switch (repeat) { case Repeat.Daily: for (int i = 1; i <= occurrences; i++) result.Add(localStart.AddDays(i)); break; case Repeat.Every2Weeks: for (int i
  • 是否存在针对“实数”类型的C#通用约束? [复制](Is there a C# generic constraint for “real number” types? [duplicate])
    问题 这个问题已经在这里有了答案: 8年前关闭。 可能重复: 仅整数的C#通用约束 问候! 我试图在C#中设置笛卡尔坐标系,但我不想将自己的坐标值限制为任何一种数值类型。 有时它们可​​以是整数,而有时它们可​​以是有理数,具体取决于上下文。 这让我大叫“通用类”,但是我对如何将类型限制为整数和浮点感到困惑。 我似乎找不到涵盖任何实数概念的课程... public class Point<T> where T : [SomeClassThatIncludesBothIntsandFloats?] { T myX, myY; public Point(T x, T y) { myX = x; myY = y; } } Point<int> pInt = new Point<int>(5, -10); Point<float> pFloat = new Point<float>(3.14159, -0.2357); 如果我想要这种自由度,我是否在选课时要进​​行“ typeof(T)”噩梦,清除掉布尔值,字符串,对象等? 或更糟糕的是,我是否选择为要使用的每种数字创建一个类,并且每种数字都使用相同的内部数学公式? 任何帮助,将不胜感激。 谢谢! 回答1 您无法定义这样的约束,但是可以在运行时检查类型。 但是,这不会帮助您进行计算。 如果要进行计算,则可以选择如下所示: class
  • C#为打开的文件计算MD5?(C# calculate MD5 for opened file?)
    问题 如何计算进程打开或使用的文件的 MD5 哈希? 文件可以是txt或exe 我当前的 exe 代码返回错误,因为它正在运行 这是我当前的代码 public static string GetMd5HashFromFile(string fileName) { FileStream file = new FileStream(fileName, FileMode.Open); MD5 md5 = new MD5CryptoServiceProvider(); byte[] retVal = md5.ComputeHash(file); file.Close(); StringBuilder sb = new StringBuilder(); for (int i = 0; i < retVal.Length; i++) { sb.Append(retVal[i].ToString("x2")); } return sb.ToString(); } 干杯。 回答1 尝试以只读方式打开文件: FileStream file = new FileStream(fileName, FileMode.Open, FileAccess.Read); 或者: FileStream file = File.OpenRead(fileName); 这将取决于其他文件句柄的共享模式。
  • C#计算特定应用程序的CPU使用率(c# calculate CPU usage for a specific application)
    问题 我试图弄清楚如何获取特定进程的CPU使用率,但只能找到与总体CPU使用率有关的信息。 有谁知道如何以百分比形式提取特定应用程序的当前CPU使用率? 回答1 性能计数器-进程-处理器时间百分比。 小样代码让您有一个主意: using System; using System.Diagnostics; using System.Threading; namespace StackOverflow { class Program { static void Main(string[] args) { PerformanceCounter myAppCpu = new PerformanceCounter( "Process", "% Processor Time", "OUTLOOK", true); Console.WriteLine("Press the any key to stop...\n"); while (!Console.KeyAvailable) { double pct = myAppCpu.NextValue(); Console.WriteLine("OUTLOOK'S CPU % = " + pct); Thread.Sleep(250); } } } } 根据流程ID查找实例的注意事项: 我不知道有什么更好的方法,希望有人能做到。 如果没有
  • 在 C# 中计算文件内容的哈希? [复制](Calculate the Hash of the Contents of a File in C#? [duplicate])
    问题 这个问题在这里已经有了答案: 如何从文本文件创建 MD5 哈希摘要? (4 个回答) 7年前关闭。 我需要在 C# 中计算文件内容的哈希值吗? 所以,我可以在我的应用程序中比较两个文件哈希。 我有搜索但没有找到。 回答1 您可以使用MD5CryptoServiceProvider ,它可以处理基于文本的文件以及二进制文件。 byte[] myFileData = File.ReadAllBytes(myFileName); byte[] myHash = MD5.Create().ComputeHash(myFileData); 或者...如果您处理大文件并且不想将整个文件加载到内存中: byte[] myHash; using (var md5 = MD5.Create()) using (var stream = File.OpenRead(myFileName)) myHash = md5.ComputeHash(stream); 您可以使用Enumerable.SequenceEqual与来自两个文件的字节数组进行比较: myHash1.SequenceEqual(myHash2); 您也可以尝试创建一个 CRC 计算器。 见:http://damieng.com/blog/2006/08/08/calculating_crc32_in_c_and_net 回答2
  • 如何根据 C# 和 .NET 中的周数获取月份(How to get the month depending on the week number in C# and .NET)
    问题 如何根据指定的周数获得月份? 例如,如果获取周数2返回月1 ( January )? 回答1 取周数乘以 7。例如,如果是周数 12,则将 12 乘以 7。这将表示它已经过的天数,四舍五入到最接近的周。 将此数字除以 30。在示例中,我们通过计算得出的数字是 84。84 除以 30 是 2.8 使用这个数字来计算月份。 2.8 表示现在是三月。 小数点前的数字表示过去的月份。 始终将数字四舍五入,这将为您提供当前月份。 阅读更多:http://www.ehow.com/how_7444970_calculate-month-week-number.html#ixzz2zYJVK4S8 回答2 好吧,首先我们应该达成协议; 由于一周可以从一个月开始并在第二个月结束,让我们以不同的方法找出给定的一周开始和结束的月份。 让我们实现WeekStart :给定一个date ,我们想找出对应的一周开始日期: private static DateTime WeekStart(DateTime date, DayOfWeek firstDayOfWeek) { DayOfWeek current = date.DayOfWeek; return (current >= firstDayOfWeek) ? date.Date.AddDays(firstDayOfWeek - current)
  • 倾斜位图,RGB565 C#的步幅计算(Slanted bitmap, stride calculation for RGB565 C#)
    问题 我得到的一些图像是倾斜的,有些不是。 预期结果:(529x22) 实际结果:(529x22) 不要介意不同的图像大小,这些是屏幕截图。 它们都是 529x22。 我正在使用的代码,我只是从 SO 上的一个问题的答案中得到的。 // some other method byte[] pixels = new byte[size - 16]; Array.Copy(this.data, offset, pixels, 0, pixels.Length); this.ByteToImage(w, h, pixels); // builds the pixels to a image private Bitmap ByteToImage(int w, int h, byte[] pixels) { var bmp = new Bitmap(w, h, PixelFormat.Format16bppRgb565); var BoundsRect = new Rectangle(0, 0, bmp.Width, bmp.Height); BitmapData bmpData = bmp.LockBits(BoundsRect, ImageLockMode.WriteOnly, bmp.PixelFormat); // bytes => not using this because it
  • C# - 如何计算特定哈希算法的 ASN.1 DER 编码?(C# - How to calculate ASN.1 DER encoding of a particular hash algorithm?)
    问题 给定像 SHA1 或 SHA256 这样的哈希算法,我将如何获取 RFC3447 中定义的 ASN.1 DER 编码? (参见第 42 页 - 链接)以下是所需的输出。 MD5 30 20 30 0c 06 08 2a 86 48 86 f7 0d 02 05 05 00 04 10 SHA-1 30 21 30 09 06 05 2b 0e 03 02 1a 05 00 04 14 SHA-256 30 31 30 0d 06 09 60 86 48 01 65 03 04 02 01 05 00 04 20 SHA-384 30 41 30 0d 06 09 60 86 48 01 65 03 04 02 02 05 00 04 30 SHA-512 30 51 30 0d 06 09 60 86 48 01 65 03 04 02 03 05 00 04 40 我希望在 C# 中有一些智能方法可以做到这一点,不需要我编写 Oid 到 ASN.1 DER 转换例程(或对它们进行硬编码)。 有任何想法吗? 回答1 这将使您成为其中的一部分: string oidString = CryptoConfig.MapNameToOID(hashName); // f.x. "MD5" byte[] encodedOid = CryptoConfig.EncodeOID