Edit: I had to use union for that purpose specifically, because the chapter is about them. The fragment of the first task which the one I speak of is based on:
Design a union named byte_set, which allows you to break up a number of type int so that all its component bytes can be displayed. The size of the union must be equal to the size of the int type, while the number of fields of the byte_set union must not exceed two.
Include the union declarations in the byte_set.h file.
Test its operation for an int number with the value 0x41424344 by displaying the values of its consecutive bytes.
I'm currently learning about unions in C99.
My task was this:
Read an int by user, and then display it as:
- 2x word
- 4x bytes
- 4x 8 bits (4 octets from Most Significant Bit, to Least Significant Bit)
With the following restrictions:
- without using bitwise operators,
- without using
[]
operator to read arrays,- using only one
if
(ternary op. is forbidden).
My solution passes the tests fine, but I wanted to ask if there is any way to make it more compact in displaying the bit values.
My solution was this:
#include <stdio.h>
struct byte{
unsigned char bit0:1;
unsigned char bit1:1;
unsigned char bit2:1;
unsigned char bit3:1;
unsigned char bit4:1;
unsigned char bit5:1;
unsigned char bit6:1;
unsigned char bit7:1;
};
union bit_set{
unsigned int number;
unsigned short word[2];
unsigned char byte[4];
struct byte bytes[4];
};
int main() {
union bit_set bit_set = {0};
setvbuf(stdout, NULL, _IONBF, 0);
printf("Podaj liczbę: ");
if(!scanf("%u", &bit_set.number)){
printf("Incorrect input");
return 1;
}
printf("%u\n", bit_set.number);
printf("%d %d\n", *bit_set.word, *(bit_set.word+1));
printf("%d %d %d %d\n", *bit_set.byte, *(bit_set.byte+1), *(bit_set.byte+2), *(bit_set.byte+3));
for(int i = 0; i < 4; i++){
printf("%d", (bit_set.bytes+i)->bit7);
printf("%d", (bit_set.bytes+i)->bit6);
printf("%d", (bit_set.bytes+i)->bit5);
printf("%d", (bit_set.bytes+i)->bit4);
printf("%d", (bit_set.bytes+i)->bit3);
printf("%d", (bit_set.bytes+i)->bit2);
printf("%d", (bit_set.bytes+i)->bit1);
printf("%d", (bit_set.bytes+i)->bit0);
printf(" ");
}
return 0;
}
struct byte{
unsigned char bit0:1;
};
union bit_set{
unsigned int number;
unsigned short word[2];
unsigned char byte[4];
struct byte bits[32];
};
// ...
for(int i = 0; i < 4; i++){
for (int j = 7; j > 0; j--) {
printf("%d", (bit_set.bits+j)->bit0);
}
printf(" ");
}
Enter a number: 1
it produces:
1
1 0
1 0 0 0
0000000 0000000 0000000 0000000
Enter a number: 2
it produces:
2
2 0
2 0 0 0
0000000 0000000 0000000 0000000
In C, a struct
object has a minimum size of 1 byte.
Therefore, in the code
struct byte{
unsigned char bit0:1;
};
union bit_set{
unsigned int number;
unsigned short word[2];
unsigned char byte[4];
struct byte bits[32];
};
the member bits
is an array of 32 elements of struct byte
, in which each element has a size of 1 byte. The total size of that array is therefore 32 bytes. You seem to expect the size of the array to be 32 bits, i.e. 4 bytes.