70 likes | 304 Views
CS 192. Lecture 19 Winter 2003 February 09-10, 2004 Dr. Shafay Shamail. Unions. Look just like structures and have same syntax Use union keyword instead of struct Like a struct, can hold different data types, BUT only one type at a time i.e. members share storage
E N D
CS 192 Lecture 19 Winter 2003 February 09-10, 2004 Dr. Shafay Shamail
Unions • Look just like structures and have same syntax • Use union keyword instead of struct • Like a struct, can hold different data types, BUT only one type at a time i.e. members share storage • Like Sayeed Saigol (auditorium) can hold different classes, but only one at a time • Also, Sayeed Saigol’s size is equal to the largest class size • But better than building a different room for each class; saves space • Likewise, a union is automatically allocated memory as large as the largest data type it contains as its member • Saves memory
Unions #include <iostream.h> union int_or_double{ int x; double y; }; void main() { int_or_double number;/**only 8 bytes for a double allocated**/ number.x = 100;/**store as int**/ cout << number.x<<endl<<number.y<<endl; number.y = 100.0; /**store as double. int value lost**/ cout<<number.x<<endl<<number.y<<endl; } • Output: 100 -9.25596e+061 0 100 //2nd and 3rd values are junk • This output is system dependent. System tries to read the number at the memory location in the format you apply. Succeeds for the correct type, junk for the wrong type • Try with int x and float y. Same storage space required for both, but still garbage values. • Programmer is responsible for storing and interpreting properly
Unions #include <iostream.h> union int_or_char{ int x; char y; }; void main() { int_or_char value; value.x = 97;//store as int cout << value.x<<endl<<value.y<<endl; value.y = 'b';//store as char cout<<value.x<<endl<<value.y<<endl; } • Output:97 a 98 b • Can do all the things that we can do with a struct • Union can have a struct as a member, and vice versa
Unions • First initializer stored as the data type of the first member #include <iostream.h> union int_or_double{ int x; double y; }; void main() { int_or_double number; number.x = 100.3; cout << number.x<<endl<<number.y<<endl; number.y = 100; cout<<number.x<<endl<<number.y<<endl; } • Output: 100 junk junk 100 • Apart from memory, unions also useful where you know a value will be either one of two types e.g. you can have a union for items that have either a char name[20] or an int serial_no
Bit Fields • An int or unsigned member of a structure or union can be declared to consist of a specified no. of bits • Such a member is called a bit field, and the no. of associated bits is called its width • struct card{ unsigned pips : 4;//can’t do so outside struct/union unsigned suit : 2; }; • How many values can we store in 4 and 2 bits? • 2nvalues (0 thru 2n-1) in n bits • Conserves memory: how many things storable in 6 bits or 1 byte? Only a character • Here, 64 1-bit variables using bit fields • The width is at most the no. of bits in a machine word
An example that uses bit fields for cards and outputs them. Also note how array of struct passed as usual array #include <iostream.h> #include <iomanip.h> struct BitCard { unsigned face : 4; unsigned suit : 2; }; void fillDeck(BitCard *); void deal(BitCard *); main() { BitCard deck[52]; fillDeck(deck); deal(deck); return 0; } void fillDeck(BitCard *wDeck) { for (int i = 0; i <= 51; i++) { wDeck[i].face = i % 13; wDeck[i].suit = i / 13; } } /** Output cards in two column format. Cards 0 25 subscripted with k1 in column 1. Cards 26-51 subscripted with k2 in column 2 **/ void deal(BitCard *wDeck) { for (int k1 = 0, k2 = k1 + 26; k1 <= 25; k1++, k2++) { cout << "Card:" << setw(3) << wDeck[k1].face << " Suit:"<< setw(2) << wDeck[k1].suit << " "; cout << "Card:" << setw(3) << wDeck[k2].face << " Suit:"<< setw(2) << wDeck[k2].suit << endl; } }