1. 首页
  2. > 香港公司年审 >

二进制1010101对应的十进制(将二进制数1010101转换成十进制数)


创建头文件3-1.h


#define FUNC(type) type type##Func() #define CALL_FUNC(type) type##Func() FUNC(void); FUNC(char); FUNC(int); FUNC(float);



创建 3-1.cpp 文件:


#include "3-1.h" #include <iostream> using namespace std; FUNC(void) { cout << "void voidFunc() 被调用" << endl; } FUNC(char) { cout << "char charFunc() 被调用" << endl; return a; } FUNC(int) { cout << "int intFunc() 被调用" << endl; return 3; } FUNC(float) { cout << "float floatFunc() 被调用" << endl; return 3.14; }



创建含有main函数的.cpp文件:


#include "3-1.h" #include <iostream> using namespace std; int main() { CALL_FUNC(void); char a = CALL_FUNC(char); cout << "返回值为" << a << endl; int b = CALL_FUNC(int); cout << "返回值为" << b << endl; float c = CALL_FUNC(float); cout << "返回值为" << c << endl; }



输出:


void voidFunc() 被调用 char charFunc() 被调用 返回值为a int intFunc() 被调用 返回值为3 float floatFunc() 被调用 返回值为3.14



3-2

编写一个程序使用两重for循环和模运算符(%)去寻找和输出质数(只能被1和它本身整除的整数)。




#include <iostream> using namespace std; int main() { cout << "请输入一个整数:"; int a; cin >> a; cout << "在2到" << a << "之间有如下质数:" << endl; for (int i = 2; i <=a; i ) { bool isPrime = true; for (int j = 2; j < i; j ) { if (i % j == 0) {//能整除,说明不是质数 isPrime = false; break; } } if (isPrime) { cout << i << " "; } } cout << endl; }



输出:


请输入一个整数:20 在2到20之间有如下质数: 2 3 5 7 11 13 17 19



3-3

编写一个程序,使用一个while循环从标准输入(cin)中把单词读入到string中。这是一个“无穷”while循环,可以使用break语句中断(和退出程序)。对于读入的每个单词,先用一系列的if语句把该单词“映射”为一个整数值,然后用该整数值作为一个switch语句的选择条件(这些操作并不意味着良好的设计风格,这仅仅是为练习这些控制流程)。在每个case中,输出一些有意义的信息。判定哪些是“有趣”的单词以及这些单词的意义。同时判定哪个单词是程序结束的标志。用文件作为输入来测试该程序(如果想节省输入,这个文件将作为程序的源文件)。


#include <iostream> #include <string> using namespace std; int main() { string word; while (cin >> word) { if (word == "quit") { cout << "退出程序"; break; } int type = 0; if (word.size() == 5) { type = 1; } else if (word.size() > 5) { type = 2; } switch (type) { case 0: cout << word << ":这个单词长度小于5" << endl; break; case 1: cout << word << ":是个有趣的单词,长度等于5" << endl; break; case 2: cout << word << ":这个单词长度大于5" << endl; break; } } }



输出:


what what:这个单词长度小于5 are are:这个单词长度小于5 you you:这个单词长度小于5 doing doing:是个有趣的单词,长度等于5 quit 退出程序



3-4

修改Menu.cpp程序,使用switch语句代替if语句。


#include <iostream> using namespace std; int main() { char c; // To hold response while(true) { cout << "主菜单:" << endl; cout << "l: 左, r: 右, q: 退出 -> "; cin >> c; if (c == q) break; switch (c) { case l: { cout << "左键菜单:" << endl; cout << "选择 a 或 b:"; cin >> c; switch (c) { case a: cout << "你选择了a" << endl; continue; // Back to main menu case b: cout << "你选择了b" << endl; continue; // Back to main menu default: cout << "你没有选择 a 或 b!" << endl; continue; // Back to main menu } break; } case r: { cout << "右键菜单:" << endl; cout << "选择 c 或 d: "; cin >> c; switch (c) { case c: cout << "你选择了c" << endl; continue; // Back to main menu case d: cout << "你选择了d" << endl; continue; // Back to main menu default: cout << "你没有选择 c 或 d!" << endl; continue; // Back to main menu } break; } } cout << "你必须选择 l 或 r 或 q!" << endl; } cout << "退出菜单..." << endl; }



3-5

编写一个程序计算在“优先级”一节中的两个表达式的值。


#include <iostream> using namespace std; #define PRINT(X) cout << #X " = " << X << endl; int main() { int X = 1, Y = 2, Z = 3; PRINT(X Y - 2/2 Z); PRINT(X (Y - 2)/(2 Z)); }



输出:


X Y - 2/2 Z = 5 X (Y - 2)/(2 Z) = 1



3-6

修改YourPets2.cpp程序以使用不同的数据类型(char、int、float、double和这些类型的变型)。运行该程序并画出结果内存分布图。如果能在多种机器、操作系统或者编译器上运行该程序,用尽可能多的变化进行这个试验。


#include <iostream> using namespace std; #define PRINT(type) cout << #type " 大小:" << sizeof(type) << endl; #define PRINT_ADDR(x, y, z) cout << &x << " " << &y << " " << &z << endl; int main() { char ci, cj, ck; short int si, sj, sk; int i, j, k; long int li, lj, lk; long long lli, llj, llk; float fi, fj, fk; double di, dj, dk; long double ldi, ldj, ldk; PRINT(char); // PRINT_ADDR(ci, cj, ck); 不可以直接使用cout << &ci 这种形式打印地址,因为 // &ci,会变成一个char*指针,而使用cout << (char *) 会被认为要打印一个字符数组, // 所以为了打印,可能把它转成void*来打开地址。 cout << (void*)&ci << " " << (void*)&cj << " " << (void*)&ck << endl; PRINT(short int);PRINT_ADDR(si, sj, sk); PRINT(int);PRINT_ADDR(i, j, k); PRINT(long int);PRINT_ADDR(li, lj, lk); PRINT(long long);PRINT_ADDR(lli, llj, llk); PRINT(float);PRINT_ADDR(fi, fj, fk); PRINT(double);PRINT_ADDR(di, dj, dk); PRINT(long double);PRINT_ADDR(ldi, ldj, ldk); }



输出:


char 大小:1 0xbce13ff83f 0xbce13ff83e 0xbce13ff83d short int 大小:2 0xbce13ff83a 0xbce13ff838 0xbce13ff836 int 大小:4 0xbce13ff830 0xbce13ff82c 0xbce13ff828 long int 大小:4 0xbce13ff824 0xbce13ff820 0xbce13ff81c long long 大小:8 0xbce13ff810 0xbce13ff808 0xbce13ff800 float 大小:4 0xbce13ff7fc 0xbce13ff7f8 0xbce13ff7f4 double 大小:8 0xbce13ff7e8 0xbce13ff7e0 0xbce13ff7d8 long double 大小:16 0xbce13ff7c0 0xbce13ff7b0 0xbce13ff7a0



3-7

创建两个函数,一个接受一个string*参数,另一个接受一个string&参数。每个函数必须用它特有的方式去改变外部的string对象。在main()中,创建和初始化一个string对象,输出它,然后把它传给每个函数,输出结果。


#include <iostream> #include <string> using namespace std; void modify(string* ps) { *ps = "string* " *ps; } void modify(string& rs) { rs = "string& " rs; } int main() { string a("hello"); cout << "原始字符串:" << a << endl; modify(&a); cout << "用指针改变:" << a << endl; modify(a); cout << "用引用改变:" << a << endl; }



输出:


原始字符串:hello 用指针改变:string* hello 用引用改变:string& string* hello



3-8

编写一个使用所有三个图形字符(trigraph)的程序,看看你的编译器是否支持它们。


trigraph是什么,看一下这个[文章](https://blog.csdn.net/daheiantian/article/details/6095507)。


#include <iostream> using namespace std; int main() { cout << "??=" << endl;//如果支持,应该输出# cout << "??(" << endl;//如果支持,应该输出[ cout << "??)" << endl;//如果支持,应该输出] cout << "??<" << endl;//如果支持,应该输出{ cout << "??>" << endl;//如果支持,应该输出} cout << "??/" << endl;//如果支持,应该输出/ cout << "??!" << endl;//如果支持,应该输出| cout << "??" << endl;//如果支持,应该输出^ cout << "??-" << endl;//如果支持,应该输出~ }



使用如下makefile编译:


CPP = g OFLAG = -o .SUFFIXES : .o .cpp .c .cpp.o : $(CPP) $(CPPFLAGS) -c $< .c.o : $(CPP) $(CPPFLAGS) -c $< 3-8: 3-8.o $(CPP) $(OFLAG) $@ $^ rm $^ ./$@ 3-8.o: 3-8.cpp



输出:


3-8.cpp:5:14: warning: trigraph ??= ignored, use -trigraphs to enable [-Wtrigraphs] 5 | cout << "??=" << endl;//如果支持,应该输出# | 3-8.cpp:6:14: warning: trigraph ??( ignored, use -trigraphs to enable [-Wtrigraphs] 6 | cout << "??(" << endl;//如果支持,应该输出[ | 3-8.cpp:7:14: warning: trigraph ??) ignored, use -trigraphs to enable [-Wtrigraphs] 7 | cout << "??)" << endl;//如果支持,应该输出] | 3-8.cpp:8:14: warning: trigraph ??< ignored, use -trigraphs to enable [-Wtrigraphs] 8 | cout << "??<" << endl;//如果支持,应该输出{ | 3-8.cpp:9:14: warning: trigraph ??> ignored, use -trigraphs to enable [-Wtrigraphs] 9 | cout << "??>" << endl;//如果支持,应该输出} | 3-8.cpp:10:14: warning: trigraph ??/ ignored, use -trigraphs to enable [-Wtrigraphs] 10 | cout << "??/" << endl;//如果支持,应该输出/ | 3-8.cpp:11:14: warning: trigraph ??! ignored, use -trigraphs to enable [-Wtrigraphs] 11 | cout << "??!" << endl;//如果支持,应该输出| | 3-8.cpp:12:14: warning: trigraph ?? ignored, use -trigraphs to enable [-Wtrigraphs] 12 | cout << "??" << endl;//如果支持,应该输出^ | 3-8.cpp:13:14: warning: trigraph ??- ignored, use -trigraphs to enable [-Wtrigraphs] 13 | cout << "??-" << endl;//如果支持,应该输出~ | g -o 3-8 3-8.o rm 3-8.o ./3-8 ??= ??( ??) ??< ??> ??/ ??! ?? ??-



按照提示,使用-trigraphs来编译,修改makefile:


CPP = g OFLAG = -o #加一个CPPFLAGS CPPFLAGS = -trigraphs .SUFFIXES : .o .cpp .c .cpp.o : $(CPP) $(CPPFLAGS) -c $< .c.o : $(CPP) $(CPPFLAGS) -c $<



把cpp文件第10行转义一下:


cout << "??/" << endl;//如果支持,应该输出/



输出:


# [ ] { } | ^ ~



3-9

编译和运行Static.cpp程序。从代码中删除static关键词,再次编译和运行,解释发生的现象。


#include <iostream> using namespace std; void func() { int i = 0; cout << "i = " << i << endl; } int main() { for(int x = 0; x < 10; x ) func(); }



输出:


i = 1 i = 1 i = 1 i = 1 i = 1 i = 1 i = 1 i = 1 i = 1 i = 1



删除了static关键字之后,i变成了一个普通的局部变量,每次调用func函数时,都会初始化为0,输出时加1,所以每次调用都输出1。


3-10

试编译FileStatic.cpp和FileStatic2.cpp程序并把它们连接起来。得到的错误消息的含义是什么?


错误消息是:


D:/msys64/mingw64/bin/../lib/gcc/x86_64-w64-mingw32/10.3.0/../../../../x86_64-w64-mingw32/bin/ld.exe: FileStatic2.o:FileStatic2.cp:(.rdata$.refptr.fs[.refptr.fs] 0x0): undefined reference to `fs



未定义fs引用,也就是说fs定义找不到。因为在FileStatic.cpp中,fs是static的,只能文件内可见,所以在FileStatic2.cpp中虽然声明了fs,但是在连接步骤,连接器是找不到的。


3-11

修改Boolean.cpp程序,用double值代替int值。


#include <iostream> using namespace std; int main() { double i,j; cout << "Enter an double: "; cin >> i; cout << "Enter another double: "; cin >> j; cout << "i > j is " << (i > j) << endl; cout << "i < j is " << (i < j) << endl; cout << "i >= j is " << (i >= j) << endl; cout << "i <= j is " << (i <= j) << endl; cout << "i == j is " << (i == j) << endl; cout << "i != j is " << (i != j) << endl; cout << "i && j is " << (i && j) << endl; cout << "i || j is " << (i || j) << endl; cout << " (i < 10) && (j < 10) is " << ((i < 10) && (j < 10)) << endl; }



3-12

修改Boolean.cpp和Bitwise.cpp程序,使用显示运算符(如果你的编译器与C 标准兼容,那么它会支持这些运算符)。


Boolean.cpp


#include <iostream> using namespace std; int main() { int i,j; cout << "Enter an integer: "; cin >> i; cout << "Enter another integer: "; cin >> j; cout << "i > j is " << (i > j) << endl; cout << "i < j is " << (i < j) << endl; cout << "i >= j is " << (i >= j) << endl; cout << "i <= j is " << (i <= j) << endl; cout << "i == j is " << (i == j) << endl; cout << "i != j is " << (i not_eq j) << endl; cout << "i && j is " << (i and j) << endl; cout << "i || j is " << (i or j) << endl; cout << " (i < 10) && (j < 10) is " << ((i < 10) and (j < 10)) << endl; }



Bitwise.cpp


#include "printBinary.h" #include <iostream> using namespace std; // A macro to save typing: #define PR(STR, EXPR) cout << STR; printBinary(EXPR); cout << endl; int main() { unsigned int getval; unsigned char a, b; cout << "Enter a number between 0 and 255: "; cin >> getval; a = getval; PR("a in binary: ", a); cout << "Enter a number between 0 and 255: "; cin >> getval; b = getval; PR("b in binary: ", b); PR("a | b = ", a bitor b); PR("a & b = ", a bitand b); PR("a ^ b = ", a xor b); PR("~a = ", compl a); PR("~b = ", compl b); // An interesting bit pattern: unsigned char c = 0x5A; PR("c in binary: ", c); a or_eq c; PR("a |= c; a = ", a); b and_eq c; PR("b &= c; b = ", b); b xor_eq a; PR("b ^= a; b = ", b); }



3-13

使用在Rotation.cpp程序中的函数去修改Bitwise.cpp程序。确保用这种方式能清楚地显示在旋转过程中的结果。


#include "printBinary.h" #include <iostream> using namespace std; // A macro to save typing: #define PR(STR, EXPR) cout << STR; printBinary(EXPR); cout << endl; extern unsigned char rol(unsigned char val); extern unsigned char ror(unsigned char val); int main() { unsigned char a; cout << "输入一个 0 到 255 之间的数: "; cin >> a; cout << (int)a << endl; PR("当前数的二进制: ", a); cout << "开始左转:" << endl; for (int i = 0; i < 8; i ) { a = rol(a); PR("左转1位:", a); } PR("当前数的二进制:", a) cout << "开始右转:" << endl; for (int i = 0; i < 8; i ) { a = ror(a); PR("右转1位:", a); } }



输出:


当前数的二进制: 01100001 开始左转: 左转1位:11000010 左转1位:10000101 左转1位:00001011 左转1位:00010110 左转1位:00101100 左转1位:01011000 左转1位:10110000 左转1位:01100001 当前数的二进制:01100001 开始右转: 右转1位:10110000 右转1位:01011000 右转1位:00101100 右转1位:00010110 右转1位:00001011 右转1位:10000101 右转1位:11000010 右转1位:01100001



3-14

修改Ifthen.cpp程序,使用三重if-else运算符(?:)。


#include <iostream> using namespace std; int main() { int i; cout << "type a number and Enter" << endl; cin >> i; i > 5 ? cout << "Its greater than 5" << endl : i < 5 ? cout << "Its less than 5 " << endl : cout << "Its equal to 5 " << endl; cout << "type a number and Enter" << endl; cin >> i; i < 10 ? i > 5 ? cout << "5 < i < 10" << endl : cout << "i <= 5" << endl : cout << "i >= 10" << endl; }



3-15

创建一个含有两个string对象和一个int对象的struct。使用typedef为该struct命名。创建struct的一个实例,初始化实例的三个值,然后输出它们。获得实例的地址,然后赋值给定义的struct类型的指针。改变实例的三个值,然后通过指针把它们打印出来。


#include <iostream> #include <string> using namespace std; typedef struct { string a; string b; int c; } MyStruct; int main() { MyStruct a; a.a = "hello"; a.b = "world"; a.c = 100; cout << a.a << " " << a.b << " " << a.c << endl; MyStruct *pa; pa = &a; pa->a = "Hello"; pa->b = "World"; pa->c = 200; cout << pa->a << " " << pa->b << " " << pa->c << endl; }



输出:


hello world 100 Hello World 200



3-16

编制一个使用颜色枚举类型的程序。创建一个enum类型的变量,然后用for循环输出与颜色名对应的数字。


#include <iostream> using namespace std; enum Color { COLOR_MIN, BLACK, WHITE, RED, GREEN, BLUE, COLOR_MAX }; int main() { Color color = RED; for (int i = COLOR_MIN 1; i < COLOR_MAX; i ) { if (i == color) { cout << i << endl; break; } } }



3-17

用Union.cpp程序做一个试验,删除各种union元素,观察对union大小的影响。试给该union的一个元素赋值(属于某一类型),然后通过不同的元素(属于不同的类型)输出它的值,看看发生了什么情况。


#include <iostream> using namespace std; union Packed { // Declaration similar to a class char i; short j; int k; long l; float f; double d; // The union will be the size of a // double, since thats the largest element }; // Semicolon ends a union, like a struct int main() { cout << "sizeof(Packed) = " << sizeof(Packed) << endl; Packed x; x.i = c; cout << x.i << endl; cout << x.j << endl; cout << x.k << endl; cout << x.l << endl; cout << x.f << endl; cout << x.d << endl; }



因为short, int , long与char存储格式一致,所以都能够正确输出char c的十进制数,但是由于浮点数的格式不一样,所以无法正确输出c对应十进制数99的浮点数。


输出:


sizeof(Packed) = 8 c 99 99 99 1.38729e-43 4.89125e-322



union大小是元素里类型字节占用最大的大小,在本cpp中就是double,占用8个字节,如果你删除l, f, d元素,那么大小就会变成int k的字节大小,也就是4个字节。


3-18

编制一个程序,连续定义两个int数组。第二个数组的开始下标紧接第一个数组的结束下标。给两个数组赋值。打印出第二个数组观察由此引起的变化。再在两个数组定义之间定义一个char变量,重复上述操作。可以创建一个数组输出函数以简化程序。


NND,我愣是没看懂啥意思


3-19

修改ArrayAddresses.cpp程序,使之能处理char、long、int、float以及double类型数据。


#include <iostream> using namespace std; int main() { char a[10]; cout << "sizeof(char) = "<< sizeof(char) << endl; for(int i = 0; i < 10; i ) cout << "&a[" << i << "] = " << (void*)&a[i] << endl; // 打印char的地址必须转换成别的类型,否则会当成字符串 long b[10]; cout << "sizeof(long) = "<< sizeof(long) << endl; for(int i = 0; i < 10; i ) cout << "&a[" << i << "] = " << &b[i] << endl; // float, double忽略了 }



输出:


sizeof(char) = 1 &a[0] = 0xb0651ff89e &a[1] = 0xb0651ff89f &a[2] = 0xb0651ff8a0 &a[3] = 0xb0651ff8a1 &a[4] = 0xb0651ff8a2 &a[5] = 0xb0651ff8a3 &a[6] = 0xb0651ff8a4 &a[7] = 0xb0651ff8a5 &a[8] = 0xb0651ff8a6 &a[9] = 0xb0651ff8a7 sizeof(long) = 4 &a[0] = 0xb0651ff870 &a[1] = 0xb0651ff874 &a[2] = 0xb0651ff878 &a[3] = 0xb0651ff87c &a[4] = 0xb0651ff880 &a[5] = 0xb0651ff884 &a[6] = 0xb0651ff888 &a[7] = 0xb0651ff88c &a[8] = 0xb0651ff890 &a[9] = 0xb0651ff894



3-20

运用ArrayAddresses.cpp程序中的技术,输出在StructArray.cpp程序中定义的struct的大小以及数组元素的地址。


#include <iostream> using namespace std; typedef struct { int i, j, k; } ThreeDpoint; int main() { ThreeDpoint a[10]; cout << "sizeof(ThreeDpoint) = "<< sizeof(ThreeDpoint) << endl; for(int i = 0; i < 10; i ) cout << "&a[" << i << "] = " << &a[i] << endl; }



输出:


sizeof(ThreeDpoint) = 12 &a[0] = 0xceb6dffbb0 &a[1] = 0xceb6dffbbc &a[2] = 0xceb6dffbc8 &a[3] = 0xceb6dffbd4 &a[4] = 0xceb6dffbe0 &a[5] = 0xceb6dffbec &a[6] = 0xceb6dffbf8 &a[7] = 0xceb6dffc04 &a[8] = 0xceb6dffc10 &a[9] = 0xceb6dffc1c



3-21

创建一个string对象数组且对每一个元素赋一个字符串。用for循环输出该数组。


#include <iostream> #include <string> using namespace std; int main() { string strArr[3]; strArr[0] = "hello"; strArr[1] = "csdn"; strArr[2] = "!"; for (int i = 0; i < 3; i ) { cout << strArr[i] << endl; } }



3-22

在ArgsToInts.cpp的基础上,编制两个新程序,它们各自使用atol()和atof()函数。


#include <iostream> #include <cstdlib> using namespace std; int main(int argc, char* argv[]) { if (argc < 3) { cout << "请输入2个参数" << endl; return 0; } cout << atol(argv[1]) << endl; cout << atof(argv[2]) << endl; }



3-23

修改PointerIncrement2.cpp程序,其中用union代替struct。


#include <iostream> using namespace std; typedef union { char c; short s; int i; long l; float f; double d; long double ld; } Primitives; int main() { Primitives p[10]; Primitives* pp = p; cout << "sizeof(Primitives) = " << sizeof(Primitives) << endl; cout << "pp = " << pp << endl; pp ; cout << "pp = " << pp << endl; }



输出:


sizeof(Primitives) = 16 pp = 0x9dc2bffbe0 pp = 0x9dc2bffbf0



3-24

修改PointerArithmetic.cpp程序,其中使用long和long double。


这个比较简章,就是替换一下变量。


#include <iostream> using namespace std; #define P(EX) cout << #EX << ": " << EX << endl; int main() { long a[10]; for(int i = 0; i < 10; i ) a[i] = i; // Give it index values long* ip = a; P(*ip); P(* ip); P(*(ip 5)); long* ip2 = ip 5; P(*ip2); P(*(ip2 - 4)); P(*--ip2); P(ip2 - ip); // Yields number of elements }



输出:


*ip: 0 * ip: 1 *(ip 5): 6 *ip2: 6 *(ip2 - 4): 2 *--ip2: 5 ip2 - ip: 4



3-25

定义一个float变量。获得它的地址,把地址转化为unsigned char,赋值给一个unsigned char指针。使用指针和[ ]符号引用float变量中的下标,并用本章中定义的printBinary()函数输出该float的内存映像。(从0到sizeof(float))。改变该float变量的值看看是否能推算出下一步的情况(float包含编码的数据)。


#include "printBinary.h" #include <iostream> using namespace std; int main() { float f = 3.5;//根据IEEE标准,实际二进制格式为01000000 01100000 00000000 00000000 unsigned char *p = (unsigned char*)&f; int len = sizeof(float)/sizeof(unsigned char); for (int i = 0; i < len; i ) { printBinary(p[i]);cout << " "; } cout << endl; for (int i = 0; i < len; i ) { printBinary(p[len - 1 - i]);cout << " "; } }



输出:


00000000 00000000 01100000 01000000 01000000 01100000 00000000 00000000



第二种输出顺序与IEEE标准的格式完全一致,第二种输出是先输出高位,然后是低位,分别对应了float字节的高位和低位,说明存储的字节序是小端字节序,即低位字节码存储在低地址上。


3-26

定义一个int数组。获得该数组的起始地址,使用static_cast把它转化为void*。写一个带以下参数的函数:一个void*、一个数字(表明字节的数目)和一个值(表明每个字节需要设定的值)。该函数必须为特定范围内的每个字节设定特定的值。在这个int数组上试验函数。


#include <iostream> using namespace std; void setArray(void *p, int size, int val) { unsigned char * pch = static_cast<unsigned char*>(p); for (int i = 0; i < size; i ) { pch[i] = val; } } int main() { const int LEN = 10; int a[LEN]; setArray(static_cast<void*>(a), sizeof(a), 1); for (int i = 0; i < LEN; i ) { cout << "a[" << i << "] = 0x" << hex << a[i] << endl; } }



输出:


a[0] = 0x1010101 a[1] = 0x1010101 a[2] = 0x1010101 a[3] = 0x1010101 a[4] = 0x1010101 a[5] = 0x1010101 a[6] = 0x1010101 a[7] = 0x1010101 a[8] = 0x1010101 a[9] = 0x1010101



3-27

建立一个const double类型数组和一个volatile double类型数组。通过引用每个数组的下标且用const_cast把每个元素分别转换为non-const和non-volatile,然后对每个元素赋值。


#include <iostream> using namespace std; int main() { const double a[10] = {0}; volatile double b[10]; for (int i = 0; i < 10; i ) { const_cast<double&>(a[i]) = i; const_cast<double&>(b[i]) = i; } for (int i = 0; i < 10; i ) { cout << a[i] << " "; } cout << endl; for (int i = 0; i < 10; i ) { cout << b[i] << " "; } cout << endl; }



输出:


0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9



3-28

建立一个函数,该函数接受一个指向double类型数组的指针和一个表明该数组大小的值。该函数应该输出数组中的每个元素值。现在建立一个double类型的数组,且初始化每个元素的值为0,然后使用你的函数输出该数组。接着使用reinterpret_cast关键字把数组的起始地址转化为unsigned char*,把每个元素设置为1(提示:必须用sizeof运算符计算一个double类型变量包含的字节数)。现在使用你的数组输出函数输出结果。想想为什么每个元素值不设成1.0?


#include <iostream> using namespace std; void displayArray(double *pa, int len) { for (int i = 0; i < len; i ) { cout << pa[i] << " "; } cout << endl; } int main() { double a[10] = {0}; unsigned char *p = reinterpret_cast<unsigned char*>(a); for (int i = 0, size = sizeof(a); i < size; i ) { p[i] = 1; } displayArray(a, 10); }



输出:


7.7486e-304 7.7486e-304 7.7486e-304 7.7486e-304 7.7486e-304 7.7486e-304 7.7486e-304 7.7486e-304 7.7486e-304 7.7486e-304



可以把1.0赋值为每个元素,但是unsigned char*只接受0~255之间的数,即使你给它赋值为1.0,也会被截断成1赋值给每个元素。


3-29

(带有挑战性)修改FloatingAsBinary.cpp程序以便能够以单独的二进制位组输出double类型数据。为实现目标,必须用自己的特殊代码(可以从printBinary()函数中衍生)去替换对printBinary()的调用,还必须查阅并理解自己的编译器的浮点数字节格式(这是具有挑战性的部分)。


单独的二进制位 应该指的是分别输出符号位、尾数、指数


3-30

创建makefile文件,可以把编译YourPets1.cpp和YourPets2.cpp程序(用你特定的编译器)以及执行这两个程序作为默认的目标,确保使用后缀规则。


3-30.makefile


CPP = g OFLAG = -o .SUFFIXES : .o .cpp .cpp.o : $(CPP) $(CPPFLAGS) -c $< all: YourPets1 YourPets2 YourPets1: YourPets1.o $(CPP) $(OFLAG)$@ $< rm $< ./$@ YourPets2: YourPets2.o $(CPP) $(OFLAG)$@ $< rm $< ./$@ YourPets1.o: YourPets1.cpp YourPets2.o: YourPets2.cpp



执行输出:


$ make -f 3-30.makefile g -c YourPets1.cpp g -oYourPets1 YourPets1.o rm YourPets1.o ./YourPets1 g -c YourPets2.cpp g -oYourPets2 YourPets2.o rm YourPets2.o ./YourPets2 char 大小:1 0x932b5ffc2f 0x932b5ffc2e 0x932b5ffc2d short int 大小:2 0x932b5ffc2a 0x932b5ffc28 0x932b5ffc26 int 大小:4 0x932b5ffc20 0x932b5ffc1c 0x932b5ffc18 long int 大小:4 0x932b5ffc14 0x932b5ffc10 0x932b5ffc0c long long 大小:8 0x932b5ffc00 0x932b5ffbf8 0x932b5ffbf0 float 大小:4 0x932b5ffbec 0x932b5ffbe8 0x932b5ffbe4 double 大小:8 0x932b5ffbd8 0x932b5ffbd0 0x932b5ffbc8 long double 大小:16 0x932b5ffbb0 0x932b5ffba0 0x932b5ffb90



3-31

修改StringizingExpressions.cpp程序,通过设置一个命令行标志,使用P(A)能用条件#ifdef与调试代码分离开。需要参数编译器文档,了解在命令行上怎样定义和取消定义预处理的值。


cpp文件:


#include <iostream> using namespace std; #ifdef LOG #define P(A) cout << #A << ": " << (A) << endl; #else #define P(A) cout << (A) << endl; #endif int main() { int a = 1, b = 2, c = 3; P(a); P(b); P(c); P(a b); P((c - a)/b); }



编译命令:


$ make -f gcc.makefile StringizingExpressions g -c StringizingExpressions.cpp g -oStringizingExpressions StringizingExpressions.o rm StringizingExpressions.o ./StringizingExpressions 1 2 3 3 1



编译命令上添加宏定义标志,需要修改makefile文件,在后缀规则前面添加下面一行,表示定义一个宏:


CPPFLAGS = -DLOG



再看输出:


$ make -f gcc.makefile StringizingExpressions g -DLOG -c StringizingExpressions.cpp g -oStringizingExpressions StringizingExpressions.o rm StringizingExpressions.o ./StringizingExpressions a: 1 b: 2 c: 3 a b: 3 (c - a)/b: 1

3-32

定义一个函数,该函数接受一个double型参数且返回一个int值。创建和初始化一个指向该函数的指针,通过这个指针调用这个函数。


#include <iostream> using namespace std; int f(double d) { cout << "int f(double d) 被调用" << endl; return 0; } int main() { int (*pf)(double); pf = f; pf(0); }



输出:


int f(double d) 被调用



3-33

声明一个函数,该函数接受一个int参数且返回指向另一个函数的指针,这个函数接受一个char变量且返回一个float值。


#include <iostream> using namespace std; float f(char a) { cout << "float f(char a) 被调用" << endl; return 0; } float (*ff(int))(char) { return f; } typedef float (*pf)(char); //或者如下声明ff也可以更简单 pf ff1(int) { return f; } int main() { pf a = ff(0); a(1); a = ff1(0); a(1); }



输出:


float f(char a) 被调用 float f(char a) 被调用



3-34

修改FunctionTable.cpp程序使每个函数返回一个string(而不是输出一个消息)以便在main()函数中输出。


#include <iostream> #include <string> using namespace std; // A macro to define dummy functions: #define DF(N) string N() { return "function " #N " called..."; } DF(a); DF(b); DF(c); DF(d); DF(e); DF(f); DF(g); string (*func_table[])() = { a, b, c, d, e, f, g }; int main() { while(1) { cout << "press a key from a to g " "or q to quit" << endl; char c; cin >> c; if ( c == q ) break; // ... out of while(1) if ( c < a || c > g ) continue; cout << (*func_table[c - a])() << endl; } }



输出:


press a key from a to g or q to quit a function a called... press a key from a to g or q to quit b function b called... press a key from a to g or q to quit c function c called... press a key from a to g or q to quit d function d called... press a key from a to g or q to quit e function e called... press a key from a to g or q to quit f function f called... press a key from a to g or q to quit g function g called... press a key from a to g or q to quit h press a key from a to g or q to quit q



3-35

为前面某个练习(自己选择)建立一个makefile文件,允许键入make以构建这个程序,并且键入make debug以构建带有调试信息的程序。


3-35.cpp


#include <iostream> using namespace std; int main() { #ifdef DEBUG cout << "debug info" << endl; #endif }



3-35.makefile:


CPP = g OFLAG = -o #CPPFLAGS = -DLOG .SUFFIXES : .o .cpp .c .cpp.o : $(CPP) $(CPPFLAGS) -c $< all: 3-35 debug: 3-35-debug 3-35: 3-35.o $(CPP) $(OFLAG)$@ $< rm $< ./$@ 3-35-debug: 3-35-debug.o $(CPP) $(OFLAG)$@ $< rm $< ./$@ 3-35.o:3-35.cpp 3-35-debug.o: 3-35.cpp $(CPP) -DDEBUG $(OFLAG)$@ -c $<



默认目标是all,所以编译不带debug信息的命令如下:


$ make -f 3-35.makefile g -c 3-35.cpp g -o3-35 3-35.o rm 3-35.o ./3-35



编译debug信息的,需要使用debug目标:


$ make -f 3-35.makefile debug g -DDEBUG -o3-35-debug.o -c 3-35.cpp g -o3-35-debug 3-35-debug.o rm 3-35-debug.o ./3-35-debug debug info

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至123456@qq.com 举报,一经查实,本站将立刻删除。

联系我们

工作日:9:30-18:30,节假日休息