简体   繁体   English

交换无符号短整数的字节

[英]Swapping bytes of unsigned short integer

I have a partially working function which involves writing to a file. 我有一个部分工作的功能,涉及写入文件。

I have an array, arr , of type unsigned short int and each element must be written to a file in binary format. 我有一个类型为unsigned short int的数组arr ,每个元素必须以二进制格式写入文件。

My inital solution was: 我的初始解决方案是:

for(i = 0; i < ROWS; i++) {
    fwrite(&arr[i], 1, sizeof(unsigned short int), source);
}

The code above works when writing unsigned short ints to the file. 上面的代码在将unsigned short ints写入文件时起作用。 Also, source is a pointer to the file which is being written to in binary format. 此外, source是指向以二进制格式写入的文件的指针。 However, I need to swap the bytes, and am having trouble doing so. 但是,我需要交换字节,并且我很难这样做。 Essentially, what is written to the file as abcd should be cdab . 基本上,作为abcd写入文件的内容应该是cdab

My attempt: 我的尝试:

unsigned short int toWrite;
unsigned short int swapped;
for(i = 0; i < ROWS; i++) {
    toWrite = &arr[i];
    swapped = (toWrite >> 8) | (toWrite << 8);

    fwrite(swapped, 1, sizeof(unsigned short int), source);
}

However I get a segmentation fault core dump as a result. 但是我得到了一个分段故障核心转储。 I read and used the upvoted answer to this question - convert big endian to little endian in C [without using provided func] - but it doesnt seem to be working. 我阅读并使用了这个问题的upvoted答案 - 在C中将大端转换为小端[不使用提供的函数] - 但它似乎没有工作。 Any suggestions? 有什么建议? Thanks! 谢谢!

your attempt is very wrong (and the answers you copied from are okay, the problem isn't in the swapping itself) 你的尝试是非常错误的(你复制的答案是可以的,问题不在于交换本身)

First you're taking the address of the value to swap, then you're passing the value instead of the address to write. 首先,您将值的地址换成交换,然后传递而不是要写入的地址。 It should be: 它应该是:

unsigned short int toWrite;
unsigned short int swapped;
for(i = 0; i < ROWS; i++){
        toWrite = arr[i];
        swapped = (toWrite >>8) | (toWrite <<8); // that part is OK
        fwrite(&swapped, 1 , sizeof(unsigned short int) , source);  
}

I'm positive that the compiler warned you for this. 我很肯定编译器警告你这个。 Warnings are useful. 警告很有用。

Welcome to the world of non portable binary formats. 欢迎来到非便携式二进制格式的世界。

Swapping the numbers is a hack that is error prone because it makes the program non portable: whether to swap the values or not depends on the endianness of the system where you compile and run the program. 交换数字是一个容易出错的黑客,因为它使程序不可移植:是否交换值取决于编译和运行程序的系统的字节顺序。 Your program has a very simple bug: you pass the value of swapped instead of its address. 你的程序有一个非常简单的错误:你传递swapped的值而不是它的地址。 You can fix it with: 你可以修复它:

fwrite(&swapped, sizeof(swapped), 1, source);

Yet a better solution for your problem is to handle endianness explicitly in your program. 然而,更好的解决方案是在程序中明确处理字节序。 This is a portable solution to write the numbers in big endian order: 这是一个以大端顺序编写数字的便携式解决方案:

/* writing 16 bit unsigned integers in big endian order */
for (i = 0; i < ROWS; i++) {
    putc(arr[i] >> 8, source);
    putc(arr[i] & 255, source);
}

This is the alternative version if you are expected to write in little endian order: 如果您希望以小端顺序写入,则这是替代版本:

/* writing 16 bit unsigned integers in little endian order */
for (i = 0; i < ROWS; i++) {
    putc(arr[i] & 255, source);
    putc(arr[i] >> 8, source);
}

Note that it is somewhat confusing to name the stream variable for an output file source . 请注意,为输出文件source命名流变量有点令人困惑。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM