在Windows下用C语言表示数据。 Big-endian&小端

时间:2015-09-05 13:58:22

标签: c fread

我有一些C代码,通过" fread"读取,但结果不是我的预期。这是我的代码:

 void main()
{
    unsigned int *data =(unsigned int*)malloc(4);
    static unsigned int ImageData[256][256];
    char *filename= "C:\\Users\\Frank\\Documents\\Visual Studio 2012\\Projects\\UI\\UI\\bin\\Debug\\bin\\result.txt";
    FILE *pfile=fopen(filename,"rb");
    for (int i = 0; i < 256; i++)
        for (int j = 0; j < 256; j++)
        {
           fread(data, 4, 1, pfile);              
           ImageData[i][j] =(*data);
        }
          fclose(pfile);        
          printf("\nsize=%d",sizeof(unsigned int));
    for (int i = 0; i < 9; i++)     
        for (int j = 0; j < 9; j++)
        {
           printf("\npixel[%d,%d]=%d",i,j,ImageData[i][j]);
        }           
}

我对十六进制的期望是:

38 FC 0D 13 38 A7 D4 92 38 1F 32 B3 38 blabla...

2 个答案:

答案 0 :(得分:1)

两个主要问题:

  1. 始终检查相关系统调用的结果,如果您依赖其结果,通常就是这种情况。

    FILE *pfile=fopen(filename,"rb");
    

    应该是

    FILE *pfile=fopen(filename,"rb");
    if (NULL == pfile)
    {
       fprintf(stderr, "%s failed to open.\n", filename);
    }
    
  2. 打印unsigned int时,请使用%u转化说明符。

    所以这个

    printf("\npixel[%d,%d]=%d", i, j,ImageData[i][j]);
    

    应该是

    printf("\npixel[%d,%d]=%u", i, j, ImageData[i][j]);
    
  3. 一些小问题:

    1. C-Standard定义main()以返回int

      所以这个

      void main()
      

      应该是

      int main()
      

      甚至更好

      int main(void)
      
    2. 无需在C中投射malloc/calloc/realloc的结果,也不以任何方式推荐。

    3. malloc()也可能失败。

      通过

      测试其结果
      data = malloc(4);
      if (NULL == data)
      {
        /* Log error and probably exit ... */
      }
      
    4. fread()也可能会失败。

      if (1 != fread(..., 4, 1, pfile))
      {
         /* read less then expected */
      }
      
    5. 衡量内存和索引数组的首选数据类型是size_t而不是int。在这种情况下,不需要负值。

    6. 最后的一些提示:

      1. 如果您知道需要读取32位值(4个字节),请确保正确定义变量。

        #include <inttypes.h> /* for u/int32_t */
        
        uint32_t ImageData[256][256];
        
      2. 无需动态分配临时读取缓冲区。

        只需定义

        uint32_t data;
        

        并像这样使用

        if (1 != fread(&data, 4, 1, pfile))
        {
           ...
        
        ImageData[i][j] = data;
        

        或直接读入数组

        if (1 != fread(&ImageData[i][j], 4, 1, pfile))
        {
           ...
        

答案 1 :(得分:0)

无论如何,这是一个很大的小端问题。以下进行了解决。

ImageData[i][j] =_byteswap_ulong(ImageData[i][j]);

谢谢大家。