Question: 我又来问代码问题啦

没人回了咩

引用 15 楼 zhao4zhong1 的回复:仅供参考：//NAME: essaie bla bla //DIMENSION: 8 //DATA //1  14  15 //2  11  10 //3  6   4 //4  7   13 //5  9   21 //6  19  3 //7  1   5 //8  8   8 //EOF // // 文本文件中可能还含有其他内容，但是需要用到的内容即以上  //比如data.txt: //NAME: essaie bla bla //其它内容 //DIMENSION: 8 //其它内容 //DATA //其它内容 //1  14  15 //其它内容 //2  11  10 //其它内容 //3  6   4 //其它内容 //4  7   13 //其它内容 //5  9   21 //其它内容 //6  19  3 //其它内容 //7  1   5 //其它内容 //8  8   8 //其它内容 //EOF  // 目标是要获取NAME后字串，DIMENSION后数值，以及DATA以下的数值 // 其中NAME就是随便个字句，DIMENSION是城市数量，DATA以下是城市编号，X坐标，Y坐标 // 所有的这些将赋值给一个事先定义好的结构 #include <stdio.h> #include <string.h> #define MAXCPL   80   //每行最大字符数 #define MAXCITY  100  //每组数据中DATA最多项数，DIMENSION的最大值 #define MAXNAMEL 32   //NAME最大长度 struct S {     char NAME[MAXNAMEL+1];     int  DIMENSION;     struct D {         int NO;         int X;         int Y;     } DATA[MAXCITY]; } s; FILE *f; int st,n,i; char ln[MAXCPL]; int main() {     f=fopen("data.txt","r");     if (NULL==f) {         printf("Can not open file data.txt!\n");         return 1;     }     st=0;     n=0;     while (1) {         if (NULL==fgets(ln,MAXCPL,f)) break;         if (st==0) {             if (1==sscanf(ln,"NAME: %32[^\n]",s.NAME)) st=1;         } else if (st==1) {             if (1==sscanf(ln,"DIMENSION: %d",&s.DIMENSION)) st=2;         } else if (st==2) {             if (0==strcmp(ln,"DATA\n")) st=3;         } else if (st==3) {             if (3==sscanf(ln,"%d%d%d",&s.DATA[n].NO,&s.DATA[n].X,&s.DATA[n].Y)) {                 n++;                 if (n>=MAXCITY || n>=s.DIMENSION) break;             }         }     }     fclose(f);     printf("s.NAME=[%s]\n",s.NAME);     printf("s.DIMENSION=%d\n",s.DIMENSION);     for (i=0;i<n;i++) {         printf("s.DATA[%d].NO,X,Y=%d,%d,%d\n",i,s.DATA[i].NO,s.DATA[i].X,s.DATA[i].Y);     }     return 0; } //s.NAME=[essaie bla bla] //s.DIMENSION=8 //s.DATA[0].NO,X,Y=1,14,15 //s.DATA[1].NO,X,Y=2,11,10 //s.DATA[2].NO,X,Y=3,6,4 //s.DATA[3].NO,X,Y=4,7,13 //s.DATA[4].NO,X,Y=5,9,21 //s.DATA[5].NO,X,Y=6,19,3 //s.DATA[6].NO,X,Y=7,1,5 //s.DATA[7].NO,X,Y=8,8,8   现在是执行类似“f=fopen("data.txt","r");”语句是就会出错，像16楼图中显示的那样

引用 11 楼 baidu_27937801 的回复:那要怎么解决呢？刚学到文件操作不是很懂！ fp_r的操作放在判断成功打开之后不就行了。反正你现在是打开出错，GetLastError看为什么吧。 http://baike.baidu.com/link?url=pDireFii3z21QJ8ih6qGjcu6HRYo9gDO87KT8dvjoyYVFF-ojlOyFPq9kAv-b6Od2sq7tYCz9slf1UqJ6K20EK  int iError = 0; fp_r = fopen("stu.txt", "r"); if ( fp_r== NULL)//文件读指针fp_r指向文件信息区,打开方式为读 { iError = GetLastError(); printf("文件打开失败！\n");//打开失败提示语 exit(0); } rewind(fp_r); //。。。。。。。。。

引用 12 楼 bjym1987 的回复://又来问，又不注意代码格式

//又来问，又不注意代码格式

引用 10 楼 tpnndhqc 的回复:[quote=引用 8 楼 baidu_27937801 的回复:] [quote=引用 6 楼 tpnndhqc 的回复:] [quote=引用 5 楼 baidu_27937801 的回复:] 在数据追加模块里，运行到  “head = read_file();” 这一行代码是显示无法读取内存. 你的这行read_file代码不是一个函数么，加个断点先进去看看具体哪一行报的“无法读取内存”错。 我怀疑是rewind(fp_r);错的，跟踪下吧。[/quote] 嗯!是的![/quote] 是就行了，给分！文件指针操作在判断成功之前就敢用，你也是虎啊。。。[/quote] 那要怎么解决呢？刚学到文件操作不是很懂！

引用 8 楼 baidu_27937801 的回复:[quote=引用 6 楼 tpnndhqc 的回复:] [quote=引用 5 楼 baidu_27937801 的回复:] 在数据追加模块里，运行到  “head = read_file();” 这一行代码是显示无法读取内存. 你的这行read_file代码不是一个函数么，加个断点先进去看看具体哪一行报的“无法读取内存”错。 我怀疑是rewind(fp_r);错的，跟踪下吧。[/quote] 嗯!是的![/quote] 是就行了，给分！文件指针操作在判断成功之前就敢用，你也是虎啊。。。

引用 7 楼 baidu_27937801 的回复:就是这个样子 。。。我了个蛋疼啊，你在read_file里面打断点啊，这断点设哪的能出这样谁能看出来。 最可能的地方就是 fp_r = fopen("stu.txt", "r");失败，然后用了rewind(fp_r);所以后面根本没执行就报内存错了。 重新编译在fopen前面打断点F10看。

引用 6 楼 tpnndhqc 的回复:[quote=引用 5 楼 baidu_27937801 的回复:] 在数据追加模块里，运行到  “head = read_file();” 这一行代码是显示无法读取内存. 你的这行read_file代码不是一个函数么，加个断点先进去看看具体哪一行报的“无法读取内存”错。 我怀疑是rewind(fp_r);错的，跟踪下吧。[/quote] 嗯!是的!

就是这个样子

引用 5 楼 baidu_27937801 的回复:在数据追加模块里，运行到  “head = read_file();” 这一行代码是显示无法读取内存. 你的这行read_file代码不是一个函数么，加个断点先进去看看具体哪一行报的“无法读取内存”错。 我怀疑是rewind(fp_r);错的，跟踪下吧。

引用 3 楼 u012578046 的回复:不知道，是不是文件输入格式有问题？检查一下 在数据追加模块里，运行到  “head = read_file();” 这一行代码是显示无法读取内存.

引用 3 楼 u012578046 的回复:不知道，是不是文件输入格式有问题？检查一下  嗯好的!谢谢啦！

我想还是贴出我完整的代码吧！@Sping    大神的方法我真的试过了，真的没有返回错误类型。 下面的代码是在vc++6.0里面调试的。我开始是在vs2013里调试的，后来换到vc++6.0，执行添加功能是还是运行到fp_r=fopen("stu.txt","a+")就运行不下去了。另外上面热心解答的大神们先谢过啦哈！  #include <stdio.h> #include <stdlib.h> #include <string.h> #define L sizeof(struct student) #define FORMAT_DATA "%-8d%-8s %-8.1f %-8.1f %-8.1f %-8.2f %-8.2f\n" #define FORMAT_HEAD "\n%-8s%-9s%-9s%-9s%-9s%-9s%-9s\n" struct student    //定义学生链表结点类型 { 	long ID;//学号 	char name[12];//姓名 	float eng;//英语成绩 	float math;//数学成绩 	float computer;//计算机成绩 	float ave;//平均成绩 	float sum;//总成绩 	struct student *next; }; int n;//学生人数 /***************************录入模块******************************/ struct student *create() { 	int i; 	struct student *head, *last, *p; 	printf("请输入学生人数：\n"); 	scanf("%d", &n); 	head = (struct student*)malloc(L);//创建头结点 	last = head;//末结点指针last初始化 	for (i = 0; i < n; i++) 	{ 		p = (struct student *)malloc(L);//创建新结点 		printf("请输入学生学号：\n"); 		scanf("%d", &p->ID); 		getchar(); 		printf("请输入学生姓名：\n"); 		gets(p->name); 		printf("请输入学生英语成绩：\n"); 		scanf("%f", &p->eng); 		printf("请输入学生数学成绩：\n"); 		scanf("%f", &p->math); 		printf("请输入学生计算机成绩：\n"); 		scanf("%f", &p->computer); 		p->sum = p->eng + p->math + p->computer; 		p->ave = p->sum / 3; 		last->next = p;//插入链尾 		last = last->next;//last指针后移至末结点 	} 	last->next = NULL;//链表终止延伸 	printf("**************************************输入完成***************************"); 	return head;//返回头指针 } /******************************************输出模块****************************************/ void print(struct student *head) { 	struct student *p; 	p = head->next;//指向头结点 	printf("\n所有学生信息如下：\n"); 	printf(FORMAT_HEAD,"学号", "姓名", "英语", "数学","计算机","平均成绩","总成绩"); 	while (p != NULL) 	{ 		printf(FORMAT_DATA, p->ID, p->name, p->eng, p->math, p->computer, p->ave, p->sum);//输出当前结点包含的信息 		p= p->next;//指向下一个结点	 	} 	printf("\n*******************************输出完成!**************************\n"); } /********************************************文件保存模块******************************************/ void save_file(struct student *head) { 	FILE *fp_s; 	struct student *p; 	system("cls"); 	if ((fp_s = fopen("stu.txt", "w")) == NULL)//文件读指针fp_s指向文件信息区,打开方式为写 	{ 		printf("文件打开失败！\n");//文件打开失败提示语 		exit(0); 	} 	p = head->next; 	while (p != NULL)//输出数据到文件 	{ 		fprintf(fp_s, FORMAT_DATA, p->ID, p->name, p->eng, p->math, p->computer, p->ave, p->sum); 		p = p->next; 	} 	fclose(fp_s); 	printf("\n******************************保存完毕****************************\n"); } /*******************************************文件读取模块************************************/ struct student *read_file() { 	 	FILE *fp_r; 	struct student *head_r, *last_r, *p; 	//fp_r = fopen("stu.txt","a+"); 	if ((fp_r=fopen("stu.txt", "a+")) == NULL) 	{ 		printf("文件打开失败！\n");//打开失败提示语 		exit(0); 	} 	head_r= (struct student*)malloc(L); 	last_r = head_r; 	while (!feof(fp_r))//读取文件并创建链表 	{ 		p = (struct student *)malloc(L); 		fscanf(fp_r,"%-8d%-8s %-8f %-8f %-8f %-8f %-8f\n", &p->ID, p->name, &p->eng, &p->math, &p->computer, &p->ave, &p->sum); 		last_r->next = p; 		last_r = last_r->next; 	} 	last_r->next = NULL; 	fclose(fp_r); 	return head_r; } /***********************数据查询模块****************************/ void search(struct student *head) { 	long ID_WANTED; 	struct student *pre,*p; 	pre = head; 	p = head->next; 	printf("请输入要查找的学号："); 	scanf("%ld", &ID_WANTED); 	while (p)  //循环寻找满足输入学号的结点，并输出结点信息 	{ 		while (ID_WANTED!= p->ID && p->next != NULL)//寻找匹配的节点 		{ 			pre = p; 			p = p->next; 		} 		if (p->ID ==ID_WANTED)//输出匹配结点的信息 		{ 			printf("\n所查找的学生信息为：\n"); 			printf(FORMAT_HEAD, "学号", "姓名", "英语", "数学", "计算机", "平均成绩", "总成绩"); 			printf(FORMAT_DATA, p->ID, p->name, p->eng, p->math, p->computer, p->ave, p->sum); 			p = p->next; 		} 		else 		{ 			printf("不存在学号为%ld的学生！\n",ID_WANTED); 			break; 		} 	} 	printf("\n查找完毕！\n"); } /*************************数据删除模块***************************/ struct student *del(struct student*head) { 	long ID_WANTED; 	struct student *pre,*p; 	pre = head; 	p = head->next; 	printf("请输入要查找的学号："); 	scanf("%ld", &ID_WANTED); 	while (ID_WANTED != p->ID && p->next != NULL)//寻找匹配的节点 	{ 			pre = p; 			p = p->next; 	} 	if (p->ID == ID_WANTED)//删除匹配结点 	{ 		printf("\n将要删除的学生信息为：\n"); 		printf(FORMAT_HEAD, "学号", "姓名", "英语", "数学", "计算机", "平均成绩", "总成绩"); 		printf(FORMAT_DATA, p->ID, p->name, p->eng, p->math, p->computer, p->ave, p->sum); 		pre->next = p->next; 		free(p); 	} 	else 	    printf("不存在学号为%ld的学生！\n", ID_WANTED); 	printf("\n删除完毕！\n"); 	return head; } /**********************数据追加模块****************************/ struct student *insert() { 	int n_i; 	struct student *p_in,*head,*p,*p1; 	printf("请输入添加的学生人数：\n"); 	scanf("%d",&n_i); 	head = read_file(); 	p = head; 	p1 = p; 	while (p != NULL);//定位到链尾 	{ 		p1 = p; 		p = p->next; 	} 	while (n_i != 0) 	{ 		p_in = (struct student*)malloc(L);//创建新节点 		printf("请输入学生学号：\n"); 		scanf("%d", &p_in->ID); 		getchar(); 		printf("请输入学生姓名：\n"); 		gets(p_in->name); 		printf("请输入学生英语成绩：\n"); 		scanf("%f", &p_in->eng); 		printf("请输入学生数学成绩：\n"); 		scanf("%f", &p_in->math); 		printf("请输入学生计算机成绩：\n"); 		scanf("%f", &p_in->computer); 		p_in->sum = p_in->eng + p_in->math + p_in->computer; 		p_in->ave = p_in->sum / 3; 		p1->next = p_in;//插入链尾 		p1 = p1->next;// 		n_i--; 	} 	p1->next = NULL;//链表终止延伸 	return head; } /***************************************数据追加功能***********************************/ void function_insert() { 	struct student *head_i; 	char c; 	system("cls"); 	head_i = insert();//调用插入函数，插入数据 	save_file(head_i);//保存文件 	printf("\n\t\t添加成功！\n"); 	for (;;) 	{ 		printf("\n\t\t是否继续添加？\n输入y继续添加，输入n结束添加\n"); 		c = getchar(); 		if (c == 'n') 			break; 		else if (c == 'y') 		{ 			system("cls"); 			head_i= insert(); 			save_file(head_i); 			printf("\n\t\t添加成功！"); 		} 		else 			printf("\n请输入有效字符(y/n)!!\n"); 	} 	system("pause"); } /***************************************数据查找功能***********************************/ void function_search() { 	struct student *head_s; 	char c; 	system("cls"); 	head_s = read_file(); 	search(head_s);//调用查找函数查找数据 	for (;;) 	{ 		printf("\n\t\t是否继续查找？\n输入y继续查找，输入n结束查找\n"); 		c = getchar(); 		if (c == 'n') 			break; 		else if (c == 'y') 		{ 			system("cls"); 			search(head_s); 		} 		else 			printf("\n请输入有效字符(y/n)!!\n"); 	} 	system("pause"); } /***************************************数据删除功能***********************************/ void function_delete() { 	char c; 	struct student *head; 	system("cls"); 	head = read_file();//从文件中读取数据 	head = del(head);//调用删除函数，删除数据 	save_file(head);//保存文件 	for (;;) 	{ 		printf("\n\t\t是否继续删除？\n输入y继续删除，输入n结束删除\n"); 		c = getchar(); 		if (c == 'n') 			break; 		else if (c == 'y') 		{ 			system("cls"); 			head = read_file(); 			head = del(head); 			save_file(head); 		} 		else 			printf("\n请输入有效字符(y/n)!!\n"); 	} 	system("pause"); 	 } /*****************************************数据输出功能*********************************/ void function_output() { 	struct student *head; 	system("cls"); 	head = read_file();//读取文件中的数据，生成链表 	print(head);//输出链表中的信息 	system("pause"); } /**************************创建文件功能**************************/ void function_build() { 		struct student *head; 			system("cls "); 			head = create();//创建链表 			system("pause "); 			save_file(head);//保存数据 			system("pause "); } /**************************菜单模块*****************************/ int menu() { 	int ab; 	system("cls"); 	printf("\t\t ===================================\n"); 	printf("\t\t           学生成绩管理系统        \n"); 	printf("\t\t ===================================\n"); 	printf("\t\t   ┌─────────────—┐\n"); 	printf("\t\t   │ 1. 创建文件    2. 添加数据 │\n"); 	printf("\t\t   │                            │\n"); 	printf("\t\t   │ 3. 显示数据    4. 数据查询 │\n"); 	printf("\t\t   │                            │\n"); 	printf("\t\t   │ 5. 删除数据    0. 退出程序 │\n"); 	printf("\t\t   └─────────────—┘\n"); 	printf("\t\t请输入对应的数字以选择所需功能:"); 	scanf("%d", &ab); 	return(ab); } /********************************************主程序**************************************/ void main() { 	for (;;)//循环使用主界面，直到命令退出 	{ 		switch (menu())//调用函数 		{ 		case 1: 			function_build(); 			break; 		case 2: 			function_insert();//调用记录添加函数 			break; 		case 3: 			function_output();//调用记录输出函数 			break; 		case 4: 			function_search();//调用记录查找函数 			break; 		case 5: 			function_delete();//调用记录删除函数 			break; 		case 0: 			printf("\n\t\t感谢使用！再见！\n");//退出主程序 			printf("\n\t\t"); 			system("pause"); 			exit(0); 		} 	} 	system("pause"); }

不知道，是不是文件输入格式有问题？检查一下

喔，我看错了，有文件判断。楼主调试一下代码吧，我看着头晕了，没有看出来错误

你的程序的目录下面是否有stu.txt文件，你的程序写一个catch语句，抓取一下文件打开错误，或者判断一下文件是否存在，然后再打开。

学习了，点赞


Question: 走过路过千万不要错过，跪求大牛帮忙

大神，你懂图像配准的算法吗？求帮忙看看 我这个题目最后应该做出什么样的结果。题目：基于sift特征的图像配准算法的实现  用opencv 跟vs来实现。

引用 6 楼 chenxihayi 的回复:大神，我是做图像匹配的，不是拼接 原来匹配和拼接不是一回事呀！ 但拼接的时候不是要匹配边缘处的特征吗？ 匹配不就是除了边缘处需要匹配特征，整个画面都需要匹配特征吗？  饿了别叫妈！叫“饿了么”

大神，我是做图像匹配的，不是拼接

咳咳， 先把opencv环境配置好再说  之后再研究opencv的api， 找现成的不太可能

建议楼主先编译链接调试OpenCV自带的相关例子代码。

想知道opencv里面有关于图像配准的算法吗？

以前从未结仇过opencv啊，想知道哪个版本的好用啊?


Question: 判断出栈顺序是否正确。

直接比对，不等的部分压栈，就知道结果 #include <stdio.h> #define N (1000+10) int n,m,k, a[N],b[N],sk[N]; bool check(){     int top =0,*pa=a,*pae=a+n,*pb=b,*pbe=b+n;     while(pb!=pbe){         if(pa<pae&&*pb==*pa) {             if(top==m) return false;             ++pb,++pa;         }         else if(top&&*pb==sk[top-1]) ++pb,--top;         else if(pa<pae) {             if(top==m) return false;             sk[top++]   =*pa++;         }else return false;     }     return true; }  int main () {    scanf("%d%d%d",&m,&n,&k);    for(int i=0;i<n;i++) scanf("%d",a+i);    while(k--){         for(int i=0;i<n;i++) scanf("%d",b+i);         printf("%s\n",check() ? "YES" : "NO");    } }

奔跑吧，参考：  int N, M, K; int *Push, *Pop, *Stack; int i, j, r, s; int main(void) { 	scanf("%d%d%d", &M, &N, &K); 	Stack = malloc(sizeof(int)*M); 	Push = malloc(sizeof(int)*N); 	Pop = malloc(sizeof(int)*N); 	//读入压栈序列 	for (i = 0; i < N; i++) scanf("%d", Push + i); 	r = 0; 	while (r < K) 	{ 		//读入出栈序列 		for (j = 0; j < N; j++) scanf("%d", Pop + j); 		i = j = 0; 		s = -1; 		while (j < N) 		{ 			if (-1 == s || Stack[s] < Pop[j])  //栈若是空的或栈顶元素小于当前出栈元素，则入栈 			{  				if(s < M - 1) Stack[++s] = Push[i++]; 				else  //栈空间有限，无法继续入栈 				{ 					printf("NO\n");   					break; 				} 			} 			if (Stack[s] == Pop[j])  //出栈 			{ 				s--; 				j++; 			} 			else if (Stack[s] > Pop[j]) 			{ 				printf("NO\n"); 				break; 			} 		} 		if (j == N) printf("YES\n");  //全部都可以出栈，则序列正确 		r++; 	} 	free(Push); 	free(Pop); 	free(Stack); 	return 0; }

简单的模拟出栈入栈操作，将元素依次入栈。然后根据输入的次序依次出栈。比如给出的出栈次序是 1 4 3 7 6 2 5，首先将1入栈，发现输入数据中的第一个正好是1。将1出栈，下面是4，由于栈是空，并且刚才只把1入栈，接下来将2 3 4依次入栈，些时栈顶元素是4，与输入数据的第二个元素相等，将4出栈。然后3出栈，接下来处理7，由于此时栈顶元素是2，7大于2所以接下来将5 6 7依次入栈（栈中元素为7 6 5 2）。然后栈顶元素与输入数据的7比较相等，7出栈，然后6也相等，6出栈。此时栈中元素(5 2)，待判断的输入数据为2 5。2与栈顶元素比较2<5，所以这个序列是不可能出栈顺序。


Question: 1个2维或2个1维数组的去重复

谢谢你的回复，有个问题，为什么data是9 不是10个数么，不过你的思路很好，谢谢

这样可好：  int data_1[10] = { 2, 1, 3, 5, 2, 8, 2, 8, 9, 10 }; int data_2[10] = { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }; int data[9]; int comp(void *a, void *b) { 	return *(int*)a - *(int*)b; } int main(void) { 	int i, n; 	for (i = 1; i < 10; i++) data[i - 1] = data_1[i] * 10 + data_2[i]; 	qsort(data, 9, sizeof(int), comp);  	n = 9; 	for (i = 1; i < 9; i++) 	{ 		if (data[i] == data[i-1]) n--; 	} 	printf("%d\n", n); 	return 0; }


Question: 这是我看了一道题后，自己编的，题是会了，但是我自己之前编的有错，不弄清楚不舒服，帮我看看，谢谢

n是for的变量，在while里面不能改 k =n, i=0; while(k) a[i++] =k%10, k/=10;

你的for循环里面没有循环条件，编译器不会给你编译通过，而且不符合语法规范。

#include <stdio.h>  void main() { 	int i = 95859, j; 	int a[5]; 	for (i = 95860; i < 100000; i++) 	{ 		a[0] = i/10000; 		a[1] = i/1000%10; 		a[2] = i/100%10; 		a[3] = i/10%10; 		a[4] = i%10; 		while ((a[0] == a[4]) && (a[1] == a[3])) 		{ 				for (j = 0; j < 5; j++) 				{ 					printf("%d ", a[j]); 				} 				printf("\n"); 				return; 		} 	} }

我在你的代码for循环开始处添加一句 printf("woaino  %d  ",n); 运行结果是  原因就是n是main（）函数中的变量，对于for循环来说就属于外部全局的，所以，除了第一次，每次循环n都是从11开始，加到11后，进入while循环，执行n=n/10; n变为1，然后n++变成2，再在for循环中加到11，然后继续，所以找不到了。 只需要在for循环中添加 int m = n; 然后用m取值即可。你试试。

修改如下：  #include"stdio.h" int main() { 	int a[5]; 	int i, j, n;  	for (n = 95860;; n++) 	{ 		i = 0; 		j = n;    //用j记录n的值 		while (j>10) 		{ 			a[i++] = j % 10; 			j = j / 10; 		} 		a[i] = j; 		if (a[0] == a[4] && a[1] == a[3]) 		{ 			printf("%d%d%d%d%d\n", a[0], a[1], a[2], a[3], a[4]); 			break; 		}  	} 	/*我来说下，首先a数组是用来存放每个位上的数的，那个if是用来选数，我们现在就是要 	在95860后面开始找，找到一个数，那个数它是对称相等的，比如95859，以8位分界线 	两边的数对称相等。*/ 	return 0; }


Question: 内存申请

Windows： 崩溃的时候在弹出的对话框按相应按钮进入调试，按Alt+7键查看Call Stack即“调用堆栈”里面从上到下列出的对应从里层到外层的函数调用历史。双击某一行可将光标定位到此次调用的源代码或汇编指令处，看不懂时双击下一行，直到能看懂为止。  Linux： 进程意外退出会在当前目录下产生‘core’文件或形如‘core.数字’的文件比如‘core.1234’ 使用命令 gdb 运行程序名 core或core.数字 进入gdb然后使用bt命令 可以查看进程意外退出前函数调用的堆栈，内容为从上到下列出对应从里层到外层的函数调用历史。 如果进程意外退出不产生core文件，参考“ulimit -c core文件最大块大小”命令

引用 3 楼 zhangxiangDavaid 的回复:一种可能的修改：  #include<stdio.h> #include<malloc.h> #include<string.h> #include<stdlib.h> void func(char **p)  //更改普通变量的值，使用一级指针；更改一级指针的值，使用二级指针 { 	*p = (char *)malloc(sizeof(char)*20);  //分配20个字节 } int main(int argc, char *argv[]) { 	char *s = NULL; 	func(&s);   //传入变量的地址 	strcpy(s, "i love xiyou_linux"); 	puts(s); 	return 0; }   谢谢谢谢 自己想的太简单了 看来我真的还需要好好学习 要学的东西还好多呢

引用 2 楼 zhangxiangDavaid 的回复:解释如下：  #include<stdio.h> #include<malloc.h> #include<string.h> #include<stdlib.h> void func(char *p) { 	//这里只申请了一个字节 sizeof(char) = 1 	p = (char *)malloc(sizeof(char)); //  申请内存，但是却没有说明具体大小，是不可以的吧？ } int main(int argc, char *argv[]) { 	char *s = NULL; 	func(s);   //实参与形参的问题，s还是NULL，所以下一句出错 	strcpy(s, "i love xiyou_linux");//我觉得这里也有问题吧，这意思九是复制到首地址里了吧？ 	puts(s); 	return 0; }  所以，改正的话是 1.自定义函数func里为p申请较大的内存空间 2.再在main函数里为s申请内存  不过这样func不就没有什么用了吧

void func(char *p) //指针不能回传 改为char *&p { p=(char *)malloc(sizeof(char)); //  只分配了一个字节 }


Question: FFmpeg使用RTSP流直接保存成mp4碰到的问题

推荐一个群给你  256061378 ， ffmpeg我也正在学习中， 到这个群里问问， 好多高手。


Question: printf里有printf这什么意思

引用 10 楼 zy_dream 的回复: 貌似有些理解懂了 待我好好的在品味下 最后 我打字有时不仔细啊，有些急年轻人气血旺盛 要注意 关于自己是否适合编程的很简单的测试： 在报纸或杂志上随便找一段约1000字的文章，在Word中输入一遍。输完后再参考下面答案：  A里面有10处以上文字或标点错误 B里面没有文字或标点错误并敢为此跟人打赌 C里面没有文字或标点错误并且字体和排版完全与原稿一致 D打印在半透明的纸上和原稿重叠在一起检查一模一样，且自我感觉很有成就感  A不适合编程（理由：打字准确度偏低、粗心大意） B初级程序员（理由：打字准确度很高、认真细致、自信、理解全角半角概念） C高级程序员（理由：在B的基础上理解字体和排版也是电脑打印的重要因素、但相比D还不够偏执、精益求精、结果可验证） D软件项目经理（理由：能针对项目给出令人信服的细致到极点的需求说明和典型测试用例。用户几乎挑不出毛病。专业！）  如果想从A变成B的话，到我的资源http://download.csdn.net/detail/zhao4zhong1/4084259里面下载“适合程序员的键盘练习”

今天怎么回事，各种邀请回答问题的提示呢？什么时候开的这个功能，还是CSDN推送的！  1. 我给你的的代码稍微修改了一下，试试这样输出试试  printf("%d\n", printf("%d\n", printf("%s\n",str1)));   2.  另用man 3 printf 看看 printf的返回值。  Upon  successful  return,  these functions return the number of characters printed (not including the trailing ’\0’ used to end        output to strings).   总结，这个问题不但告诉我们printf返回值的问题，还告诉我们了printf嵌套时候的中的执行顺序。

引用 7 楼 zy_dream 的回复:[quote=引用 4 楼 sholber 的回复:] printf ("%d\n", printf ("%d\n", printf ("%d\n", printf ("%d\n", 8)))); 8 2 2 2 2 好吧 只输入了一个8 返回值补应该是8吗 为什么都是2了 printf整体也是算一次的吗？那这样想依次往外返回值应该是递加的吧[/quote]  据说printf的返回值是它所输出的字符数。但是不要忘了，"%d\n"这个控制串，不但含有要输出的数字，还有一个换行符\n，这也算一个被输出的字符哇。 哇哇嘎嘎~~~

引用 4 楼 sholber 的回复:printf ("%d\n", printf ("%d\n", printf ("%d\n", printf ("%d\n", 8)))); 8 2 2 2 2 好吧 只输入了一个8 返回值补应该是8吗 为什么都是2了 printf整体也是算一次的吗？那这样想依次往外返回值应该是递加的吧

引用 4 楼 sholber 的回复:printf ("%d\n", printf ("%d\n", printf ("%d\n", printf ("%d\n", 8)))); 又是前辈您啊让我好好感悟吧

引用 2 楼 zhangxiangDavaid 的回复:printf()的返回值就是打印的字符个数。 语句 printf("   %d\n",printf("%s",str1)); 首先， printf("%s",str1);打印出str1,返回值是9 接着 printf(" %d", 9);  打印9  谢谢，原来是这样

printf, wprintf Print formatted output to the standard output stream.  int printf( const char *format [, argument]... );  int wprintf( const wchar_t *format [, argument]... );  Routine Required Header Compatibility  printf <stdio.h> ANSI, Win 95, Win NT  wprintf <stdio.h> or <wchar.h> ANSI, Win 95, Win NT    For additional compatibility information, see Compatibility in the Introduction.  Libraries  LIBC.LIB Single thread static library, retail version  LIBCMT.LIB Multithread static library, retail version  MSVCRT.LIB Import library for MSVCRT.DLL, retail version    Return Value  Each of these functions returns the number of characters printed, or a negative value if an error occurs.  Parameters  format  Format control  argument  Optional arguments  Remarks  The printf function formats and prints a series of characters and values to the standard output stream, stdout. If arguments follow the format string, the format string must contain specifications that determine the output format for the arguments. printf and fprintf behave identically except that printf writes output to stdout rather than to a destination of type FILE.  wprintf is a wide-character version of printf; format is a wide-character string. wprintf and printf behave identically otherwise.   Generic-Text Routine Mappings  TCHAR.H Routine  _UNICODE & _MBCS Not Defined _MBCS Defined _UNICODE Defined  _tprintf printf printf wprintf    The format argument consists of ordinary characters, escape sequences, and (if arguments follow format) format specifications. The ordinary characters and escape sequences are copied to stdout in order of their appearance. For example, the line  printf("Line one\n\t\tLine two\n");   produces the output  Line one         Line two  Format specifications always begin with a percent sign (%) and are read left to right. When printf encounters the first format specification (if any), it converts the value of the first argument after format and outputs it accordingly. The second format specification causes the second argument to be converted and output, and so on. If there are more arguments than there are format specifications, the extra arguments are ignored. The results are undefined if there are not enough arguments for all the format specifications.  Example  /* PRINTF.C: This program uses the printf and wprintf functions  * to produce formatted output.  */  #include <stdio.h>  void main( void ) {    char   ch = 'h', *string = "computer";    int    count = -9234;    double fp = 251.7366;    wchar_t wch = L'w', *wstring = L"Unicode";     /* Display integers. */    printf( "Integer formats:\n"            "\tDecimal: %d  Justified: %.6d  Unsigned: %u\n",            count, count, count, count );     printf( "Decimal %d as:\n\tHex: %Xh  C hex: 0x%x  Octal: %o\n",             count, count, count, count );     /* Display in different radixes. */    printf( "Digits 10 equal:\n\tHex: %i  Octal: %i  Decimal: %i\n",             0x10, 010, 10 );     /* Display characters. */     printf("Characters in field (1):\n%10c%5hc%5C%5lc\n", ch, ch, wch, wch);    wprintf(L"Characters in field (2):\n%10C%5hc%5c%5lc\n", ch, ch, wch, wch);     /* Display strings. */     printf("Strings in field (1):\n%25s\n%25.4hs\n\t%S%25.3ls\n",    string, string, wstring, wstring);    wprintf(L"Strings in field (2):\n%25S\n%25.4hs\n\t%s%25.3ls\n",        string, string, wstring, wstring);     /* Display real numbers. */    printf( "Real numbers:\n\t%f %.2f %e %E\n", fp, fp, fp, fp );     /* Display pointer. */    printf( "\nAddress as:\t%p\n", &count);     /* Count characters printed. */    printf( "\nDisplay to here:\n" );    printf( "1234567890123456%n78901234567890\n", &count );    printf( "\tNumber displayed: %d\n\n", count ); }   Output  Integer formats:    Decimal: -9234  Justified: -009234  Unsigned: 4294958062 Decimal -9234 as:    Hex: FFFFDBEEh  C hex: 0xffffdbee  Octal: 37777755756 Digits 10 equal:    Hex: 16  Octal: 8  Decimal: 10 Characters in field (1):          h    h    w    w Characters in field (2):          h    h    w    w Strings in field (1):                  computer                      comp    Unicode                      Uni Strings in field (2):                  computer                      comp    Unicode                      Uni Real numbers:    251.736600 251.74 2.517366e+002 2.517366E+002  Address as:   0012FFAC  Display to here: 123456789012345678901234567890    Number displayed: 16   Floating-Point Support Routines |  Stream I/O Routines |  Locale Routines  See Also   fopen, fprintf, scanf, sprintf, vprintf Functions

#include<string.h> #include<stdio.h> int main() { 	char *str1="WelcomeTo\0XiyouLinux\n"; 	char str2[]="WelcomeTo\0XiyouLinux\n"; 	printf("%d\n",printf("%s",str1)); 	printf("%ld,%ld\n",strlen(str1),strlen(str2)); 	printf("%lu,%lu\n",sizeof(str1),sizeof(str2)); 	return 0; }  完整的代码是这样的 自己是在ubuntu下的 用gdb简单的调试看看 因为是初学者 所以见谅


Question: turboc++3.0 怎么把相关联的文件组织在一起运行？？

新建一个工程，导入即可

放到同一个工程源文件下即可

Project、Open Project...

猜的，编译的时候同时编译 test.c 和 lcs.c 就应该可以了。 ps. 都啥年头了还用 turbo c++?，用 clang 或 g++ 吧。


Question: 关于C程序设计中的单词计数问题 求大神解答

if (c == ' ' || c == '\n' || c == '\t') state = OUT; else if (state == OUT){ state = IN; ++nw; } 就是这几行代码把我弄晕了 思考了很久 昨天去问老师 我只能说老师也被弄晕了 然后没怎么给我讲清楚 为什么else if(state == OUT) 后面出现了state = IN

nl记录行数，nw记录单词个数，nc记录字符个数 state=IN，表明正在读入连续非空白字符(空白字符：' '、'\n'、'\t')

有没有其他的大牛愿意帮我详细解答一下

引用 4 楼 user-2 的回复:This is a test. 刚开始假定状态是不在单词中（out） 1）然后读到了T，这时（out且有一个非空白字符），表明出现了一个单词，当然要把状态改成在单词中（in），且计数加一。 然后读到h，这时（in且是非空白字符）还在单词中，不要做特别的事； 读到i，读到s，类似 然后读到第一个空白，这时（in且是空白字符），表明单词结束，所以把状态改成out； 然后又读到i，重复1）这个逻辑。  总的来说就是一个简单的状态机，根据输入（每次读到的字符）和当前状态，决定下一个状态是什么，同时做一些特定逻辑的事情（比如计数）。 大牛您好 原谅我资质愚钝 你要有时间 能不能根据题目给我详细解答一下 您这个我实在有点晕 我大一新生刚接触C语言 麻烦您了

引用 2 楼 user-2 的回复:这是一个简单的状态变换而已。 请问能不能详细解答一下

这是一个简单的状态变换而已。


Question: K&R中 宏可以节省运行时函数调用的开销。这句话如何理解呢？

崇敬先贤，但不要迷信，更不要神圣化

K&R是在八十年代写着的，被称为“圣经”。但科学技术领域里，没有一成不变的东西，不能将他们说过的认为成永远正确、后人必须严格遵守照办的“圣旨”

引用 12 楼 zhao4zhong1 的回复:VC调试时按Alt+8、Alt+7、Alt+6和Alt+5,打开汇编窗口、堆栈窗口、内存窗口和寄存器窗口看每句C对应的汇编、单步执行并观察相应堆栈、内存和寄存器变化，这样过一遍不就啥都明白了吗。 对VC来说，所谓‘调试时’就是编译连接通过以后，按F10或F11键单步执行一步以后的时候，或者在某行按F9设了断点后按F5执行停在该断点处的时候。谢谢您的耐心指导 谢谢

引用 8 楼 zhao4zhong1 的回复:计算机组成原理→DOS命令→汇编语言→C语言（不包括C++）、代码书写规范→数据结构、编译原理、操作系统→计算机网络、数据库原理、正则表达式→其它语言（包括C++）、架构……  对学习编程者的忠告： 多用小脑和手，少用大脑、眼睛和嘴，会更快地学会编程！ 眼过千遍不如手过一遍！ 书看千行不如手敲一行！ 手敲千行不如单步一行！ 单步源代码千行不如单步Debug版对应汇编一行！ 单步Debug版对应汇编千行不如单步Release版对应汇编一行！  VC调试时按Alt+8、Alt+7、Alt+6和Alt+5,打开汇编窗口、堆栈窗口、内存窗口和寄存器窗口看每句C对应的汇编、单步执行并观察相应堆栈、内存和寄存器变化，这样过一遍不就啥都明白了吗。 对VC来说，所谓‘调试时’就是编译连接通过以后，按F10或F11键单步执行一步以后的时候，或者在某行按F9设了断点后按F5执行停在该断点处的时候。 （Turbo C或Borland C用Turbo Debugger调试,Linux或Unix下用GDB调试时,看每句C对应的汇编并单步执行观察相应内存和寄存器变化。） 赵老师， 单步源代码千行不如单步Debug版对应汇编一行！ 单步Debug版对应汇编千行不如单步Release版对应汇编一行！ 这两句话如何理解？求指导

引用 9 楼 u013163178 的回复:请问楼主，同样的语句是用过程的速度快，还是用函数的速度快呢？ 比较弱，，，，，，过程调用和函数调用的区别是？

请问楼主，同样的语句是用过程的速度快，还是用函数的速度快呢？

不是所有的函数都会定义成宏

“函数调用的开销”主要是指函数调用前将函数参数、返回地址压栈，函数调用完从栈中取出返回地址并跳到该地址继续执行使用的若干条汇编指令。

引用 4 楼 A1174770492 的回复:引用 2 楼 wanguser-5 的回复:谁说getchar一定要定义为宏？我的意思是为啥K&R说的  和我查看源码不一样 人家说也只是说通常，并没说一定，C语言的实现有很多版本，glibc只是其中之一

引用 3 楼 A1174770492 的回复:引用 1 楼 zhangxiangDavaid 的回复:不是所有的函数都会定义成宏这个我肯定知道，我的意思是为啥K&R说的  和我查看源码不一样 C标准只规定了函数接口，没有规定实现，具体实现得靠各大平台，不一样正常

谁说getchar一定要定义为宏？


Question: 个人不明白为什么提交代码后会得到runtime error的结果，求指点迷津

奔跑吧，参考：  #include <stdio.h> #include <stdlib.h> int year_day[2][13] = { 	{ 0, 31, 28, 31, 30 ,31, 30, 31, 31, 30, 31, 30, 31 },    	{ 0, 31, 29, 31, 30 ,31, 30, 31, 31, 30, 31, 30, 31 },  //闰年 }; int check(int year, int month, int day) { 	int pos = ((year % 4 == 0 && year % 100 != 0) || year % 400 == 0); 	if (year > 0 && month > 0 && month <= 12 && day > 0 && day <= year_day[pos][month]) 		return 1; 	return 0; } int main(void) { 	int year, month, day; 	int i, days, pos; 	while(3 == scanf("%d%d%d", &year, &month, &day)) 	{ 		if (0 == check(year, month, day)) 		{ 			printf("Illegal date\n"); 			continue; 		} 		days = 0; 		pos = ((year % 4 == 0 && year % 100 != 0) || year % 400 == 0); 		for (i = 1; i < month; i++) days += year_day[pos][i]; 		days += day; 		printf("%d\n", days); 	} 	return 0; }

比如: 2015 -1 0

提示:年月日均不可小于等于0，但是输入的测试数据有可能出现小于0的情况哦。

引用 1 楼 focuslight 的回复:数组越界了吧 可我没发现有哪个数组越界啊，还望指点一下，谢谢

数组越界了吧

引用 2 楼 ma815841356 的回复:[quote=引用 1 楼 focuslight 的回复:] 数组越界了吧 可我没发现有哪个数组越界啊，还望指点一下，谢谢[/quote]  恩恩，我题目理解错误，谢谢


Question: 请问优先队列使用什么结构来实现的？

可以直接用数组写一个大根/小根堆。   你说的插入一个元素排一次序的方法效率太低了，是搜索插入位置和移动元素的时间为O(n)的，而堆插入元素的效率应该是O(logN)的。

引用 2 楼 fly_dragon_fly 的回复:可以参考一下STL中的priority_queue，它就是用堆实现的，插入或删除不需要排序，只是一个调整堆的过程  我就是这么想的，每次push或者pop后，对堆经行一个调整，确保是个最大堆或者是最小堆 另外一个想法就是，每次push或者pop后数组进行一个排序，排序后的数组仍然是个堆。

如果优先级别比较有限，可以用 数组 + 链表 来实现 如我以前因业务需求实现一个  task_queue 要求有优先级，高底水位控制等.   // 大概结构也就这样  #define PRI_NUM 3  // 优先级 #define PRI_LOW 0 #define PRI_NORMAL 1 #define PRI_HIGH 2   struct task_queue { 	int cur_max_pri;                       // 当前队列中存在的最大优先 (其实是为了让整个 push 与 pop 过程尽量达到 O1)        int count;                                    // 队中的task 数量, (只要应用于实现水位控制) 	task_list_t *tls[PRI_NUM];    // 链表数组        // ...       // ... } task_queue_t;  // ... // task_queue * task_queue_create(); // void task_queue_release(task_queue_t *tq);  // @pri    优先权，即 PRI_LOW, PRI_NORMAL, PRI_HIGH void task_queue_push(task_queue_t *tq, task_t *t, int pri) {    // 维护 cur_max_pri;    if (pri > tq->cur_max_pri) tq->int cur_max_pri = pri;      task_list_push_tail(tq->tsl[pri], t);    // ... }  task_t * task_queue_pop(task_queue_t *tq) {   // 获取当前优先级最大的 list    // 从list 中 pop 一个 task    task_list_t * tl = tq->tls[tq->cur_max_pri];   // ...   task_t *res = task_list_pop(tl);    // 维护 cur_max_pri;   // 如果  tq->tls[tq->cur_max_pri] == NULL, 则降级.   //    while (tq->cur_max_pri == NULL && 0 < tq->cur_max_pri)  --tq->cur_max_pri;   // ..     return res; }    总体就是 用优先级来做数组的下标

是不是用堆呢

c++ stl的优先队列使用vector作为支撑，再用pop_heap及push_heap两个全局算法对vector的元素“顺序”进行管理。

优先队列 http://blog.csdn.net/zhangxiangdavaid/article/details/30113413

用数组只是每次插入不是重新排序而是仿照链表形式给数组每个节点添加前后驱


Question: 求大神看看我的代码为什么会陷入死循环

MATFile……这些都不知道是什么？

楼主关键的错误是 for(i=50;i<1700;i+=400)          for(j=6;j<508;j+=124) {  我楼上代码加了第9行显示进度 但第20行和第30行可能应该都和其下一行的}交换位置。

void stretching(float *devpre,float *devpost,float *costs) {     int Xref,Yref;      float mad=0,diff;     int i,j,m,n,p,q,a,s=0;     int dx,dy;     for(i=50;i<1700;i+=400) {         for(j=6;j<508;j+=124) {             printf("i,j=%d,%d\n",i,j);             for(m=-100;m<=100;m++) {                 for(n=-100;n<=100;n++) {                     Xref=i+m;                     Yref=j+n;                     if((Xref>=0)&&(Xref+399<1700)&&(Yref>=0)&&(Yref+123<508)) {                         for(p=0;p<400;p++) {                             for(q=0;q<124;q++) {                                 diff=*(devpost+(j+q)*1700+(i+p))-*(devpre+(Yref+q)*1700+(Xref+p));                                 mad=mad+abs(diff);                             }                             mad=mad/(400*124);                         }                     } else {                         mad=0;                     }                     a=s*201*201+(m+100)*201+(n+100);                     *(costs+a)=mad;                 }             }         }         s++;     } }

你把代码中的值改小点啊。。。2秒钟就出结果了

主要是stretching(pre,post,cost)这个函数的问题，前面的都调试过了，不知道为什么运行很长时间都出不来结果，但是老师说20多分钟就能出来结果，我这个5个小时都没出来


Question: 数组的模式匹配算法

曲线拟合？

最小二乘法？


Question: 求组

#include<stdio.h> double fun(int n) { 	int i; 	double t=0; 	for(i=100;i<n;i*=2) 		t+=1/(i*i); 	return(t); } main() { 	int m; 	scanf("%d",&m); 	printf("%lf",fun(m));  } 为什么不能返回t的值，运行后t的值为0；

cl.exe 的错误，我倒是有点熟，好像就是C++ 6.0平台就只能打开一个调试平台。出现这个错误，就把原来打开的调试框关掉就好了。 程序本身是没有错的，也用的vc++ 6.0试了一下。看是不是你的操作问题，以后注意一下，是保存->编译->连接->运行，一般我就直接点运行，但是如果出现了编译类的错误，就要按照顺序来了

把数组a的定义放到j的赋值语句前面，这个是C的限制，C99是没问题的，但是VC不支持，也可以换个编译器，比如gcc

还有一个问题

你看错误提示啊，Int a[10];后面你多了 aa

我运行为什么会显示错误？？

完美运行，木有错误呀，楼主。

我也觉得代码没有错误，看是不是哪里的字符格式错了，有的错误不好找，就将出现错误的前几行重敲一下

没有错误，稍作修改  #include<stdio.h> int main() { 	int i, j, m; 	j = 0;//为什么在此初始化会显示错误   //没有错误 	int a[10]; 	for (i = 0; i<10; i++) 		scanf("%d", &a[i]); 	scanf("%d", &m); 	for (i = 0; i<10; i++) 	{ 		if (a[i] == m) 			j = j + 1; 	} 	printf("%d\n", j); 	return 0; }  代码功能是，统计数组中等于某值的元素个数


Question: 求助

谢谢啦，嘿嘿

两个都是返回的地址，第一个地址的存储被释放了，有地址找到地方了，可是没有东西了，第二个的没有释放，后面接着可以用

char str[]="123";   //等价于char str[4] = {'1', '2', '3', '\0'};   //位于栈区，函数调用结束，即失效 char *p1 = "123";  //字符串在常量区，常量区的内容直到程序结束才销毁


Question: 为什么创建链表不成功

修改如下：  #include<stdio.h> #include<malloc.h> struct stu { 	int num; 	float score; 	struct stu *next; }; display(struct stu *head) { 	while (head != NULL) 	{ 		//printf("%d %f\n",tail->num,tail->score); 		//tail=tail->next; 		printf("%d %g\n", head->num, head->score); 		head = head->next; 	} 	return(0); } struct stu * creatLink() { 	int num; 	float score; 	struct stu *head = NULL, *tail = NULL; 	while (1) 	{ 		printf("intput num and score:"); 		scanf("%d%f", &num, &score); 		if (num>0) 		{ 			struct stu *p; 			p = (struct stu*)malloc(sizeof(struct stu)); 			p->num = num; 			p->score = score; 			p->next = NULL; 			if (head == NULL) 			{ 				head = p; 				tail = p; 			} 			else 			{ 				tail->next = p; 				tail = p; 			} 		} 		else    //这一句不可掉了 			break; 	} 	return(head); } int main() { 	struct stu *head; 	head = creatLink(); 	display(head);  	return 0; }  输入的num若小于0，则结束创建链表


Question: 菜鸟请教一个C语言的简单问题

引用 楼主 ma815841356 的回复:请问运行如下代码，为什么结果不是输出1，2，3，4，5，6呢？  #include<stdio.h>  int main() {     int b[6]= {1,2,3,4,5,6},i;     for(i=0; i<t&&b[i]!=0; i++)         printf("%d\n",b[i]);      return 0; }  我太粗心了，庸人自扰啊

修改如下：  #include<stdio.h> int main() { 	int b[6] = { 1,2,3,4,5,6 }, i; 	/* 	for (i = 0; i<t && b[i] != 0; i++)   //t是从哪里来的？ b[i]!=0  //无用 		printf("%d\n", b[i]);*/ 	for (i = 0; i<6; i++)  		printf("%d\n", b[i]); 	return 0; }


Question: 请教验证歌德巴赫猜想的算法优化问题

事先求好素数表，运算时直接查表，这才是最快的做法。

引用 2 楼 bravery36 的回复:事先求好素数表，运算时直接查表，这才是最快的做法。  恩恩

引用 1 楼 zhangxiangDavaid 的回复:这样可好：  char primes[10000]; int i, j, n; int main(void) { 	//先找出10000以内的所有素数 	memset(primes, '1', 10000); 	for (i = 2; i < 5000; i++) 		for (j = i*2; j < 10000; j+=i) 		primes[j] = '0'; 	while (1 == scanf("%d", &n)) 	{ 		j = n / 2; 		while ('0' == primes[j] || '0' == primes[n - j]) j--; 		printf("%d %d\n", j, n - j); 	} 	return 0; }   谢谢提醒

数据最多有多少组？

这个题目明显歧视Java啊


Question: 遇见段错误怎么办

Windows： 崩溃的时候在弹出的对话框按相应按钮进入调试，按Alt+7键查看Call Stack即“调用堆栈”里面从上到下列出的对应从里层到外层的函数调用历史。双击某一行可将光标定位到此次调用的源代码或汇编指令处，看不懂时双击下一行，直到能看懂为止。  Linux： 进程意外退出会在当前目录下产生‘core’文件或形如‘core.数字’的文件比如‘core.1234’ 使用命令 gdb 运行程序名 core或core.数字 进入gdb然后使用bt命令 可以查看进程意外退出前函数调用的堆栈，内容为从上到下列出对应从里层到外层的函数调用历史。 如果进程意外退出不产生core文件，参考“ulimit -c core文件最大块大小”命令

FILE *fp=fopen("a.txt","r"); //没有判断文件打开是否成功 char buffer[4096]; fgets(buffer,sizeof(buffer),fp);  //这里没有给\0留空间, 很可能读取后, 没有\0结束. fprintf(fp,"%s",buffer);  //  前面打开是"r", 表明是只读取的, 写入肯定会失败.  并且可能由于前面没有\0结束导致访问越界.

应该是没有问题，你再试试


Question: C语言字符数组简单问题错哪？能这样写吗

不会报错，会输出不确定的值！

“多一少一”问题占程序员常犯错误的10%以上！ 避免“多一少一”问题的方法之一是将比如<10甚至<5的数代入程序片断，搬手指头心算验证一下程序到底应该写为 x、x-1、x+1中的哪个？ <、<=、==、>、>=中的哪个？  其实电脑开机后物理内存的每个字节都是可读写的，从来不会因为所谓的new、delete或malloc、free而被创建、销毁。区别仅在于操作系统内存管理模块在你读写时是否能发现并是否采取相应动作而已。操作系统管理内存的粒度不是字节而是页，一页通常为4KB。

刚进大一。。。定义【10】 确实只到【9】。

越界了，你可以打印c看看

既然是字符数组(不是字符串)，你就应该在for循环里面打印字符。 此外printf ("%c\n",c[10]);已经越界了，最大就c[9]


Question: 指针的转换问题吗

一张图帮你明白数组与指针的关系： 一维数组与指针的关系；二维数组与指针的关系

int *ptr=(int *)(&a+1); //意思是把地址强制转换成int型吗？这里不太明白  紧紧抓住指针的类型这个问题，  指针的类型决定了指针能看多远。 对数组名取地址， 那么指针指针的类型就是数组指针，+1，表示跳过一个数组的空间。

理解和讨论之前请先学会如何观察！  计算机组成原理→DOS命令→汇编语言→C语言（不包括C++）、代码书写规范→数据结构、编译原理、操作系统→计算机网络、数据库原理、正则表达式→其它语言（包括C++）、架构……  对学习编程者的忠告： 多用小脑和手，少用大脑、眼睛和嘴，会更快地学会编程！ 眼过千遍不如手过一遍！ 书看千行不如手敲一行！ 手敲千行不如单步一行！ 单步源代码千行不如单步Debug版对应汇编一行！ 单步Debug版对应汇编千行不如单步Release版对应汇编一行！  VC调试时按Alt+8、Alt+7、Alt+6和Alt+5,打开汇编窗口、堆栈窗口、内存窗口和寄存器窗口看每句C对应的汇编、单步执行并观察相应堆栈、内存和寄存器变化，这样过一遍不就啥都明白了吗。 对VC来说，所谓‘调试时’就是编译连接通过以后，按F10或F11键单步执行一步以后的时候，或者在某行按F9设了断点后按F5执行停在该断点处的时候。 （Turbo C或Borland C用Turbo Debugger调试,Linux或Unix下用GDB调试时,看每句C对应的汇编并单步执行观察相应内存和寄存器变化。）  //char (*(*x[3])())[5];//x是什么类型的变量? // //分析C语言声明，关键是搞清楚这个变量是个什么东西（函数、指针、数组）， //是函数那么剩下的就是他的参数和返回值， //是指针那剩下部分是说明他指向什么， //是数组剩下的部分就是说明数组的成员是什么类型。 //解析C语言声明规则： //从左侧第一个标识符开始，按照优先级进行结合。*表示是..的指针，const表示只读的，volatile表示可变的，[]表示是数组，()表示是函数。 // //x和[3]结合说明是一个大小为3的数组，该数组的每个元素为一类指针，该类指针指向一类函数，该类函数无参数，返回一类指针，该类指针指向一个大小为5的char型数组 #include <stdio.h> #include <typeinfo.h> char num[5]; char (*x00())[5] {     return # } int main() {     char (*(*x[3])())[5];//是个数组，大小为3     char (*(*x0  )())[5];//数组的元素，是个函数指针     char (*( x00 )())[5];//函数原型，参数为空，返回值为指针     char (*  x000   )[5];//返回值      x0 = x00;     x[0] = x0;     x[1] = x0;     x[2] = x0;     printf("typeid(x).name() is %s\n",typeid(x).name());     return 0; } //typeid(x).name() is char (* (__cdecl**)(void))[5]

&a+1 中&a的类型是 int (*)[5], 它带着维数， 跟int *不同，从地址来说就是&a+1相当于地址+1*5*4，而int *加1相当于地址+1*4

引用 2 楼 zy_dream 的回复:[quote=引用 1 楼 zhangxiangDavaid 的回复:] 关于&a的含义，请看 指针与数组 http://blog.csdn.net/zhangxiangdavaid/article/details/38085743 明白了&a之后，你就明白了ptr指向的位置， 至此，后面的输出你就清楚了 好像明白了一点 // //分析实验结果：0031FCEC与0031FCE4相差8，而sizeof(array)就是8 自己编程分析后 可以理解是 &a+1是直接指向数组地址最后吗？[/quote] 最后一个元素的下一个位置

引用 1 楼 zhangxiangDavaid 的回复:关于&a的含义，请看 指针与数组 http://blog.csdn.net/zhangxiangdavaid/article/details/38085743 明白了&a之后，你就明白了ptr指向的位置， 至此，后面的输出你就清楚了 好像明白了一点 // //分析实验结果：0031FCEC与0031FCE4相差8，而sizeof(array)就是8 自己编程分析后 可以理解是 &a+1是直接指向数组地址最后吗？


Question: 有个结构体数组二分查找法，没想通 求解

先 http://www.microsoft.com/visualstudio/chs/downloads#d-2010-express 点开Visual C++ 2010 Express下面的语言选‘简体中文’，再点立即安装  再参考C:\Program Files\Microsoft Visual Studio 10.0\VC\crt\src\bsearch.c /*** *bsearch.c - do a binary search * *   Copyright (c) Microsoft Corporation. All rights reserved. * *Purpose: *   defines bsearch() - do a binary search an an array * *******************************************************************************/  #include <cruntime.h> #include <stdlib.h> #include <search.h> #include <internal.h>  #if defined (_M_CEE) #define __fileDECL  __clrcall #else  /* defined (_M_CEE) */ #define __fileDECL  __cdecl #endif  /* defined (_M_CEE) */ /*** *char *bsearch() - do a binary search on an array * *Purpose: *   Does a binary search of a sorted array for a key. * *Entry: *   const char *key    - key to search for *   const char *base   - base of sorted array to search *   unsigned int num   - number of elements in array *   unsigned int width - number of bytes per element *   int (*compare)()   - pointer to function that compares two array *           elements, returning neg when #1 < #2, pos when #1 > #2, and *           0 when they are equal. Function is passed pointers to two *           array elements. * *Exit: *   if key is found: *           returns pointer to occurrence of key in array *   if key is not found: *           returns NULL * *Exceptions: *   Input parameters are validated. Refer to the validation section of the function. * *******************************************************************************/  #ifdef __USE_CONTEXT #define __COMPARE(context, p1, p2) (*compare)(context, p1, p2) #else  /* __USE_CONTEXT */ #define __COMPARE(context, p1, p2) (*compare)(p1, p2) #endif  /* __USE_CONTEXT */  #if !defined (_M_CEE) _CRTIMP #endif  /* !defined (_M_CEE) */  SECURITYSAFECRITICAL_ATTRIBUTE #ifdef __USE_CONTEXT void * __fileDECL bsearch_s (     REG4 const void *key,     const void *base,     size_t num,     size_t width,     int (__fileDECL *compare)(void *, const void *, const void *),     void *context     ) #else  /* __USE_CONTEXT */ void * __fileDECL bsearch (     REG4 const void *key,     const void *base,     size_t num,     size_t width,     int (__fileDECL *compare)(const void *, const void *)     ) #endif  /* __USE_CONTEXT */ {     REG1 char *lo = (char *)base;     REG2 char *hi = (char *)base + (num - 1) * width;     REG3 char *mid;     size_t half;     int result;      /* validation section */     _VALIDATE_RETURN(base != NULL || num == 0, EINVAL, NULL);     _VALIDATE_RETURN(width > 0, EINVAL, NULL);     _VALIDATE_RETURN(compare != NULL, EINVAL, NULL);          /*         We allow a NULL key here because it breaks some older code and because we do not dereference         this ourselves so we can't be sure that it's a problem for the comparison function         */      while (lo <= hi)     {         if ((half = num / 2) != 0)         {             mid = lo + (num & 1 ? half : (half - 1)) * width;             if (!(result = __COMPARE(context, key, mid)))                 return(mid);             else if (result < 0)             {                 hi = mid - width;                 num = num & 1 ? half : half-1;             }             else             {                 lo = mid + width;                 num = half;             }         }         else if (num)             return (__COMPARE(context, key, lo) ? NULL : lo);         else             break;     }      return NULL; }  #undef __fileDECL #undef __COMPARE

从mid=low+(high-low)/2;可以看出这是一个前闭后开区间，即[low,hight), 如果要调整为mid-1，需要前后闭区间即[low,high],那么个数就是high-low+1了

这跟检索区间有关，请看 http://blog.csdn.net/zhangxiangdavaid/article/details/37738423


Question: 求大侠改下程序，急，在线等

这么多代码要做什么

词法分析！编译原理的

那个程序不能用


Question: 【求助帖】用C语言编写：解N元一次方程（1

这个百度一下啊，多得很

就是行列式解方程组了，找本线代的数对着敲吧


Question: 求大神指点程序，并运行检查程序；输入2.6 0.9

代码功能归根结底不是别人帮自己看或讲解或注释出来的；而是被自己静下心来花足够长的时间和精力亲自动手单步或设断点或对执行到某步获得的中间结果显示或写到日志文件中一步一步分析出来的。 提醒：再牛×的老师也无法代替学生自己领悟和上厕所！ 单步调试和设断点调试（VS IDE中编译连接通过以后，按F10或F11键单步执行，按Shift+F11退出当前函数；在某行按F9设断点后按F5执行停在该断点处。）是程序员必须掌握的技能之一。

功能是什么？


Question: CTRL + C不能终止子进程，这是为什么呢？

因为你的父进程先于子进程结束， 子进程会转任init进程为父进程， 你打印出来的getppid的值应该是1，或者2.，   这个时候子进程默认和父进程信号屏蔽基本相同， init屏蔽了什么， 子进程也一样。 如果子进程先于父进程结束，就不会有问题。比如把exit 改成死循环。  Ps:  父子进程间的信号屏蔽问题描述不准确，忘记了， 你自己查一下资料看看。


Question: vc++

引用 5 楼 yjc_520 的回复:谢谢赵4老师，代码调通了。还想问的就是运行成功，还需编写一个pl/0的代码文件，对这个文件进行运行吗？ 不明觉厉

楼主会全盘搜索指定名称的文件在哪个文件夹吗？ 注意： pl0 plO p10 p1O pIO pI0 以上六行各不相同。

那个工程怎么弄，我就是创建的头文件，没有创建工程。那个文件是需要自己定义吗？就是没找到的文件pl0.h

这个是楼主自己的头文件吗？ 我看像第三方的库，楼主把第三方的库头文件安装到VC的头文件目录下或者你的工程文件夹中，链接库放到VC目录下或者工程目录下

没有找到头此文件


Question: 关于++运算符，哪一种方法是对的？

引用 24 楼 u012578046 的回复:[quote=引用 23 楼 void998 的回复:] 原来的写法多好的，适合后期的代码维护。 有时候，不一定要追求所谓的“效率高”“代码段“ 比如我曾经看过一份代码中，很有印象的这样写来取数组的内容的（类似，变量名可能不一样）  int nValue = globleValueArray[++User[n++].getValue[++n].m]  当时我就跪了。。。哈哈，强大[/quote] 事实，没办法，有的人就是喜欢卖弄代码技巧，完全不考虑代码要给别人看，别人维护，坑。

分开写

p[n] = p1[n]; n ++; 建议就这样写  要不就这样 i = 0; j = 0; p[i++] = p1[j++];

两种都不对，与先前想要的结果不一样吧

建议重载++，来验证一下顺序。

引用 23 楼 void998 的回复:原来的写法多好的，适合后期的代码维护。 有时候，不一定要追求所谓的“效率高”“代码段“ 比如我曾经看过一份代码中，很有印象的这样写来取数组的内容的（类似，变量名可能不一样）  int nValue = globleValueArray[++User[n++].getValue[++n].m]  当时我就跪了。。。哈哈，强大

编译器行为。结果是未定义的。。。不同的编译器结果不同。本来就不能这么写。。

引用 17 楼 lin5161678 的回复:[quote=引用 16 楼 a30037338 的回复:] [quote=引用 15 楼 lin5161678 的回复:] 在线编译器 IDEONE.COM 见识了，   你应该早点把这种强有力的证据拿出来啊[/quote]因为 置顶帖是比这个主线编译器更有力的证据  [/quote]  置顶帖没啥价值，罗里八索，很简单的东西说得无比复杂，不值一喷。

引用 16 楼 a30037338 的回复:[quote=引用 15 楼 lin5161678 的回复:] 在线编译器 IDEONE.COM 见识了，   你应该早点把这种强有力的证据拿出来啊[/quote]因为 置顶帖是比这个主线编译器更有力的证据

引用 15 楼 lin5161678 的回复:在线编译器 IDEONE.COM 见识了，   你应该早点把这种强有力的证据拿出来啊

引用 13 楼 a30037338 的回复:[quote=引用 12 楼 lin5161678 的回复:] 你见识少是你自己的问题  不是你误导别人的理由 在我没见过之前， 别人说的始终是别人说的， 你这是什么编译器， 我要自己试试。[/quote] 在线编译器 IDEONE.COM

引用 楼主 mbctb 的回复:有如下代码： p[n] = p1[n]; n ++;  我想把两行并成一行，这样： p[n++] = p1[n];  或者： p[n] = p1[n++];  哪一种是对的？或者两种都不对？  抛开对错不谈，你为什么要合并？ 仅仅为了少一行代码吗？ 你这样做会给维护带来多大困难，你知道吗？尤其是别人来维护这段代码的时候。  很多时候，代码的可读性远远比代码性能重要。 PS：目前还没有遇到过因为强调可读性而导致性能下降，无法验收的情况！！！！切记切记

引用 12 楼 lin5161678 的回复:你见识少是你自己的问题  不是你误导别人的理由 在我没见过之前， 别人说的始终是别人说的， 你这是什么编译器， 我要自己试试。

引用 10 楼 a30037338 的回复:我看过， 我想说的是谁见过哪个操作系统中或者用什么编译器， 使 p[n++] = p1[n];    不等价于 p[n] = p1[n]; n ++; 反正我没见过 你见识少是你自己的问题  不是你误导别人的理由

引用 7 楼 lin5161678 的回复:你学学楼主去看看置顶帖再说 我看过， 我想说的是谁见过哪个操作系统中或者用什么编译器， 使 p[n++] = p1[n];    不等价于 p[n] = p1[n]; n ++; 反正我没见过

分两行写  p[n] = p1[n]; n ++;

引用 4 楼 Minikinfish 的回复:关于++，-- 标准C++定义为 1、在前，变量首先自增，然后再计算表达式 2、在后，首先计算表达式，然后变量自增  但是，有的编译器有bug，比如vc++6.0，无法计算出连续三个前++  例如 int a = ++n + ++n + ++n； 所以，论坛中有个赵四老师说过，尽量不要写自己都无法确定结果的表达式，该用()的加()不是编译器BUG 别信口雌黄

引用 2 楼 a30037338 的回复:两种都可以实现你想要的结果。别误导楼主  你学学楼主去看看置顶帖再说


Question: n个不同大小的结构体应该用什么数据结构管理?

异质链表 http://www.baigoogledu.com/s.php?hl=zh-CN&q=%D2%EC%B9%B9%C1%B4%B1%ED

老师,能否再具体说明一下,谢谢.

链表，存指针。


Question: 怎样把C语言数组中存放的四个十六进制数合并成一个十六进制数，并转换成十进制？

typdef union {     int addr;     char part[4]; } ip; ip ip1; ip1.part[0] = 0x01; ip1.part[1] = 0x02; ip1.part[2] = 0x03; ip1.part[3] = 0x04; printf("%d\n", ip.addr); 注意大小端。

引用 5 楼 zhangxiangDavaid 的回复:[quote=引用 3 楼 zhao4zhong1 的回复:] 楼上应转无符号，并乘256  #pragma warning(disable:4305 4309) #include <stdio.h> #include <string.h> char sDec[4] = {0x05,0xc5,0xb3,0xea}; //怎样把 0x05,0xc5,0xb3,0xea 组合成一个十六进制数 0x05c5b3ea ， //并且把 0x05c5b3ea  转换成十进制数。 unsigned int i,v; int main() {     v=0;     for (i=0;i<4;i++) v|=((unsigned int)sDec[3-i]&0xFFu)<<(i*8);     printf("0x%x,%u\n",v,v);     return 0; } //0x5c5b3ea,96842730 //  为什么要转无符号？[/quote] 因为char的取值范围通常为-128～127

char sDec[4] = {0x05,0xc5,0xb3,0xea}; unsigned char * s=(unsigned char *)sDec; int y =s[0]<<24 | s[1]<<16 | s[2]<<8 | s[3];

直接强制转换试试啊   char sc[] = {0x05, 0xc5, 0xb3, 0xea}; int *a = (int *)sc; printf("0x%X %d\n", *a, *a);   是不是发现字节序不对？转一下字节序就ok了，可以自己写函数转字节序，也可以用现成的的nothl/htonl

char sDec[4] = {0x05,0xc5,0xb3,0xea};  低字节序的情况下.  并且 int  占用 32bit.   char sDec[4] = {0x05,0xc5,0xb3,0xea};  int val = 0; char *pBuf = (char*)&val; pBuf[0] = sDec[3]; pBuf[1] = sDec[2]; pBuf[2] = sDec[1]; pBuf[3] = sDec[0];  这时val==0x05c5b3ea;   如果是高字节序那就更简单了.  char sDec[4] = {0x05,0xc5,0xb3,0xea}; int val = *(int*)sDesc;

引用 3 楼 zhao4zhong1 的回复:楼上应转无符号，并乘256  #pragma warning(disable:4305 4309) #include <stdio.h> #include <string.h> char sDec[4] = {0x05,0xc5,0xb3,0xea}; //怎样把 0x05,0xc5,0xb3,0xea 组合成一个十六进制数 0x05c5b3ea ， //并且把 0x05c5b3ea  转换成十进制数。 unsigned int i,v; int main() {     v=0;     for (i=0;i<4;i++) v|=((unsigned int)sDec[3-i]&0xFFu)<<(i*8);     printf("0x%x,%u\n",v,v);     return 0; } //0x5c5b3ea,96842730 //  为什么要转无符号？

略改： #pragma warning(disable:4305 4309) #include <stdio.h> #include <string.h> char sDec[4] = {0x05,0xc5,0xb3,0xea}; //怎样把 0x05,0xc5,0xb3,0xea 组合成一个十六进制数 0x05c5b3ea ， //并且把 0x05c5b3ea  转换成十进制数。 unsigned int i,v; int main() {     v=0;     for (i=0;i<4;i++) v|=((unsigned int)sDec[3-i]&0xFFu)<<(i*8);     printf("0x%08x,%u\n",v,v);     return 0; } //0x05c5b3ea,96842730 //

/* char sDec[4] = {0x05,0xc5,0xb3,0xea}; 怎样把 0x05,0xc5,0xb3,0xea 组合成一个十六进制数 0x05c5b3ea ， 并且把 0x05c5b3ea  转换成十进制数。 */ int main(void) { 	char sDec[4] = { 0x05,0xc5,0xb3,0xea }; 	char *c = malloc(sizeof(int)); 	c[0] = sDec[3]; 	c[1] = sDec[2]; 	c[2] = sDec[1]; 	c[3] = sDec[0]; 	int *i= (int*)c; 	printf("i=%#x\n", *i); 	printf("i=%d\n", *i); 	return 0; } //i=0x5c5b3ea //i=96842730

char * psdec = sDec;  sDec[0]+sDec[1]*255+sDec[2]*255*255+sDec[3]*255*255*255


Question: srand函数应该放在main函数中 还是放在 调用rand()函数的子函数中呢？

提醒楼主：rand()函数返回值在0～32676之间！ 如果需要扩大该范围，参考下面： #include <stdio.h> #include <stdlib.h> #include <time.h> unsigned long ulrand(void) {     return (      (((unsigned long)rand()<<24)&0xFF000000ul)     |(((unsigned long)rand()<<12)&0x00FFF000ul)     |(((unsigned long)rand()    )&0x00000FFFul)); } unsigned __int64 ullrand(void) {     return (      (((unsigned __int64)ulrand())<<32)     | ((unsigned __int64)ulrand())); } int i; unsigned long ul; unsigned __int64 ull; void main() {     srand(time(NULL));     for (i=0;i<10;i++) {         ul=ulrand();         printf("%010lu 0x%08x\n",ul,ul);     }     for (i=0;i<10;i++) {         ull=ullrand();         printf("%020I64u 0x%016I64x\n",ull,ull);     } } //3971076432 0xecb1d150 //2433428051 0x910b2a53 //1415415336 0x545d8628 //1312330759 0x4e389407 //1845758378 0x6e0409aa //0008069933 0x007b232d //4202720757 0xfa806df5 //2669855255 0x9f22c217 //0312068736 0x1299ca80 //2084555989 0x7c3fccd5 //03502077880857307931 0x3099e1472040ab1b //16884702393146816355 0xea52835e19b43763 //01877364819396611730 0x1a0dbd5b45f34e92 //07839440151924835771 0x6ccb4948756a05bb //09471412086917299176 0x8371371c820bfbe8 //04411255971577469925 0x3d37edef2f321be5 //13735846279546091130 0xbe9f876a65b7367a //04512980766520059820 0x3ea15418aa9927ac //15821377118299441610 0xdb90d2a9f1bb49ca //15512417228822200185 0xd7472d480398bf79

引用 3 楼 zhangxiangDavaid 的回复:看到源码，似乎明白了些什么 知道看源码的重要性了吧。

谢谢zhao4zhong1 虽然还是有疑惑 但至少知道怎么用了

看到源码，似乎明白了些什么

楼上胡扯！   放在main函数开始的地方调且只调一次！  C:\Program Files\Microsoft Visual Studio 10.0\VC\crt\src\rand.c /*** *rand.c - random number generator * *       Copyright (c) Microsoft Corporation. All rights reserved. * *Purpose: *       defines rand(), srand() - random number generator * *******************************************************************************/  #include <cruntime.h> #include <mtdll.h> #include <stddef.h> #include <stdlib.h>  /*** *void srand(seed) - seed the random number generator * *Purpose: *       Seeds the random number generator with the int given.  Adapted from the *       BASIC random number generator. * *Entry: *       unsigned seed - seed to seed rand # generator with * *Exit: *       None. * *Exceptions: * *******************************************************************************/  void __cdecl srand (         unsigned int seed         ) {         _getptd()->_holdrand = (unsigned long)seed; }   /*** *int rand() - returns a random number * *Purpose: *       returns a pseudo-random number 0 through 32767. * *Entry: *       None. * *Exit: *       Returns a pseudo-random number 0 through 32767. * *Exceptions: * *******************************************************************************/  int __cdecl rand (         void         ) {         _ptiddata ptd = _getptd();          return( ((ptd->_holdrand = ptd->_holdrand * 214013L             + 2531011L) >> 16) & 0x7fff ); }

里面也用得到，问题你只是在启动的时候srand了啊。如果性能允许，建议每次rand之前都srand一把


Question: STL 那种容器能够添加不同大小的结构体？

引用 10 楼 yangyunzhao 的回复:[quote=引用 9 楼 ri_aje 的回复:] 容器里存储指针就行。  存指针不安全  最笨但是肯定可行的办法就是序列化为std::string存放。用的时候反序列化为对象  所以不是不能做，而是他想找个更好的方法[/quote] 变 string 只能更不安全。 万变不离其宗，搞来搞去都是怎么在内存中动态的放置对象，本质还是指针。

引用 9 楼 ri_aje 的回复:容器里存储指针就行。  存指针不安全  最笨但是肯定可行的办法就是序列化为std::string存放。用的时候反序列化为对象  所以不是不能做，而是他想找个更好的方法

将不同大小的结构体内容序列化成string 然后vector<string>

引用 3 楼 guoyunfei1 的回复:vector <string> 是可以.  如果是结构体， 这个结构体里面有变长数组，好像就不行了。 例如： typedef  struct StruInfo StruData {      int count;      int array[]; }  然后给StruData赋值； 再添加到vector里； vector < StruData>  vecStruct: vecStruct.push_back( );  试了好像不行。  直接std::vector<int> array不行吗？  虽然很多人把c和c++混为一谈，但是两者之间还是有很多区别的。。。

只能放指针了

容器里存储指针就行。

引用 3 楼 guoyunfei1 的回复:vector <string> 是可以.  如果是结构体， 这个结构体里面有变长数组，好像就不行了。 例如： typedef  struct StruInfo StruData {      int count;      int array[]; }  然后给StruData赋值； 再添加到vector里； vector < StruData>  vecStruct: vecStruct.push_back( ); 试了好像不行。 这里的int array[];是C程序员的一个技巧

汗，你都stl了，vector了，你还用变长数组来搞毛？

引用 1 楼 yangyunzhao 的回复:std::vector<std::string>  你能说vector里面的string全部一样大吗？ 当然一样大！楼主想要的应该是tuple


Question: 运行结果出现一个提示：出现了一个问题，导致程序停止正常工作，请关闭该程序。

崩溃的时候在弹出的对话框按相应按钮进入调试，按Alt+7键查看Call Stack即“调用堆栈”里面从上到下列出的对应从里层到外层的函数调用历史。双击某一行可将光标定位到此次调用的源代码或汇编指令处，看不懂时双击下一行，直到能看懂为止。  代码功能归根结底不是别人帮自己看或讲解或注释出来的；而是被自己静下心来花足够长的时间和精力亲自动手单步或设断点或对执行到某步获得的中间结果显示或写到日志文件中一步一步分析出来的。 提醒：再牛×的老师也无法代替学生自己领悟和上厕所！ 单步调试和设断点调试（VS IDE中编译连接通过以后，按F10或F11键单步执行，按Shift+F11退出当前函数；在某行按F9设断点后按F5执行停在该断点处。）是程序员必须掌握的技能之一。


Question: LZMA算法

什么意思呢？  求楼主解答，正在做这块

引用 4 楼 wlcshh 的回复:[quote=引用 3 楼 zhao4zhong1 的回复:] [quote=引用 2 楼 wlcshh 的回复:] 我怀疑直接是作者故意，其他地方都很详细，就这里不详细， 特别是这里：0     1    lc, lp and pb in encoded form.一个字节怎么就能表示三个参数的编码形式， 而这里说的编码形式其他地方未见说明 比如lc占3位，lp占3位，pb占2位，共8位。[/quote] 问题已解决，但不是你说的这个了，不过还是谢谢[/quote] 无意间暴露了我靠瞎猜骗分的脆弱内心！

引用 3 楼 zhao4zhong1 的回复:[quote=引用 2 楼 wlcshh 的回复:] 我怀疑直接是作者故意，其他地方都很详细，就这里不详细， 特别是这里：0     1    lc, lp and pb in encoded form.一个字节怎么就能表示三个参数的编码形式， 而这里说的编码形式其他地方未见说明 比如lc占3位，lp占3位，pb占2位，共8位。[/quote] 问题已解决，但不是你说的这个了，不过还是谢谢

引用 2 楼 wlcshh 的回复:我怀疑直接是作者故意，其他地方都很详细，就这里不详细， 特别是这里：0     1    lc, lp and pb in encoded form.一个字节怎么就能表示三个参数的编码形式， 而这里说的编码形式其他地方未见说明 比如lc占3位，lp占3位，pb占2位，共8位。

outPropsSize -      In:  the pointer to the size of outProps buffer; *outPropsSize = LZMA_PROPS_SIZE = 5.      Out: the pointer to the size of written properties in outProps buffer; *outPropsSize = LZMA_PROPS_SIZE = 5.    LZMA Encoder will use defult values for any parameter, if it is   -1  for any from: level, loc, lp, pb, fb, numThreads    0  for dictSize


Question: 新人求助一c语言

偶遇到类似问题都是用 “每次用/*...*/注释掉不同部分再重新编译，直到定位到具体语法出错的位置。” 的方法解决的。


Question: 各位大牛好，请教5000万并发的服务器配置

谢谢楼上各大牛的指导！ 目前项目有了些业务需求上的变动，变动后对数据中心的要求降低了不少，在可控范围内。  再次感谢楼上各位大牛的指教，谢谢了！祝好！

看你具体需求

其实吧，一朵云，全搞定。

传输的数据如果要保存的话，硬盘柜是跑不掉了，做成阵列，速度是没问题，不过一定要用数据库。 服务器区的光纤也跑不掉了。 ms我觉得有点悬（PS.牛人能用起来我也没什么好说的），用开源的或者针对业务定制吧，前后台分开，后台SAN分流，前台IP分流。  大伙觉得我这设想怎么样

谢谢“xxyj6450 ”的建议！ 一个人我是没这能力，水都搅不浑。  这些预算我感觉并不算多（没实际接触硬件商），国内几个区域的机房建设、中心机房的建设，关硬件就得花不少，还有网络、软件服务商等等，省着点用，希望够用就好。  网络架构方面，有点思路，但还有些细节不确定，到时候具体问题具体请教，呵呵。 如果实在不行，只能请团队了。  谢谢大家了！下周回来结贴。

别去想你一个人 弄几台服务器就能搞定

有700万预算 花200W请专业的团队来做 其余的建设硬件

总站，一级基站，二级基站，三级基站....  我瞎扯的，别听我的... 楼主最后把自己的做法贴出来哈

引用 7 楼 hutliu 的回复:这个后台不用负载均衡和服务器集群很难实现。即便用固态硬盘，单台服务器一般每秒也处理不了这么多的并发io。  谢谢您的指教！  单台服务器肯定不行，肯定要用多台服务器，我想把全国分为几个区，然后每台服务器负责一个区的数据接入。

我自己在亚马逊的ec2实测写入速度有160MB/s，网络超过1.2Gb/s，所以理论上是有可能的。不过lz的数据比较奇怪，非语音还这么大数据量，感觉太多了。

这么大的数据，围观一下，不知道有没有解决方案

谢谢“dooX8086”大牛指导！深感受益！

楼主的服务器需要处理  70M/秒 数据. 但真的是要 70M/秒 的数据落地。。。。。。。。 70M x 60s x 60m x 24h x 365d = ......这个就是真的天文数字   我的大规模并发处理经验一般 实施和接触过的方案大体都是可分为三部份。 数据服   逻辑服   网关服(平衡负载), 这样的分布式可横向扩展的方案 io 压力大就添加 数据服 逻辑cpu 过高，就添加 逻辑服 ....  楼主可到 霸爷 云风 他们的 blog上翻一翻.或是 email 他们问问 ...

引用 12 楼 user-10 的回复:[quote=引用 11 楼 tonforce 的回复:] [quote=引用 8 楼 zhao4zhong1 的回复:] 关键什么样的专线才能保证70MB/s的真实流量7×24小时不中断不超时呢？直接拉光纤？  赵老师，谢谢！ 直接拉光纤，那成本天文数字了。。。[/quote] 你们的成本是多少呢？[/quote]  预算在700万内。

引用 11 楼 tonforce 的回复:[quote=引用 8 楼 zhao4zhong1 的回复:] 关键什么样的专线才能保证70MB/s的真实流量7×24小时不中断不超时呢？直接拉光纤？  赵老师，谢谢！ 直接拉光纤，那成本天文数字了。。。[/quote] 你们的成本是多少呢？

引用 8 楼 zhao4zhong1 的回复:关键什么样的专线才能保证70MB/s的真实流量7×24小时不中断不超时呢？直接拉光纤？  赵老师，谢谢！ 直接拉光纤，那成本天文数字了。。。

引用 2 楼 tonforce 的回复:谢谢赵老师的指导！ 赵老师的意思是这在逻辑上就不通？  [quote=引用 1 楼 zhao4zhong1 的回复:] “5万台终端发送的数据，其中有1000台终端是每秒发送20次数据，剩下的终端每秒发送1次数据，每次发送的数据大小均为1K左右” (1000*20+(50000-1000)*1)*1024字节/秒＝70656000字节/秒≈71MB/秒 参考：机械硬盘的传输速率≈50MB/秒[/quote] 如果你需要将数据保存到机械硬盘上的话。

引用 4 楼 zhao4zhong1 的回复:楼主帖子标题是5000万 帖子内容是5万  赵老师，这是我的失误，谢谢你的提醒！是5万台设备，不是5000万。 表示歉意！  改不过来了。


Question: UDP 服务端程序，在ARM和PC上表现结果不一样，咋回事？

换了块板子  就OK了  估计是内核版本问题导致的，，，，

及tcpdump

建议楼主先学会使用抓包软件比如wireshark


Question: 赵4老湿你来。

这题很简单，其实在其它cpp文件中有一个类似char c[10];的定义

拇指和食指组成一把枪, 一般用来表示瞄准目标, 即作用对象(LS) 同时竖起小指, 小指代表鄙视. 因此代表 鄙视LS   食指单独使用, 是一种比拇指和食指组合使用更直接的指示目标的方式. 中指单独使用, 表示f*ck. 食指和中指组合表示 f*ck xxx~~  #include "stdio.h" #define nyaa int #define nyaanyaa main() #define wowowo { #define nyanyanya } #define ohshit printf #define cat ( #define dog ) #define wo ; #define hit return #define ls 0; nyaa nyaanyaa wowowo ohshit cat "nyaa~" dog wo hit ls nyanyanya

偶咋跑到76楼了难道是点引用的时候点错楼层，造成的

引用 72 楼 zhao4zhong1 的回复:既然不给分，不水白不水： 给“从来就不关心C程序编译之后是什么样子”的码农当头棒喝！  十字链表交换任意两个节点C源代码（C指针应用终极挑战）http://download.csdn.net/detail/zhao4zhong1/5532495  好吧，我给你1分，总够意思了吧？

既然不给分，不水白不水： 给“从来就不关心C程序编译之后是什么样子”的码农当头棒喝！  计算机组成原理→DOS命令→汇编语言→C语言（不包括C++）、代码书写规范→数据结构、编译原理、操作系统→计算机网络、数据库原理、正则表达式→其它语言（包括C++）、架构……  对学习编程者的忠告： 多用小脑和手，少用大脑、眼睛和嘴，会更快地学会编程！ 眼过千遍不如手过一遍！ 书看千行不如手敲一行！ 手敲千行不如单步一行！ 单步源代码千行不如单步Debug版对应汇编一行！ 单步Debug版对应汇编千行不如单步Release版对应汇编一行！  单步类的实例“构造”或“复制”或“作为函数参数”或“作为函数返回值返回”或“参加各种运算”或“退出作用域”的语句对应的汇编代码几步后，就会来到该类的“构造函数”或“复制构造函数”或“运算符重载”或“析构函数”对应的C/C++源代码处。  VC调试时按Alt+8、Alt+7、Alt+6和Alt+5,打开汇编窗口、堆栈窗口、内存窗口和寄存器窗口看每句C对应的汇编、单步执行并观察相应堆栈、内存和寄存器变化，这样过一遍不就啥都明白了吗。 对VC来说，所谓‘调试时’就是编译连接通过以后，按F10或F11键单步执行一步以后的时候，或者在某行按F9设了断点后按F5执行停在该断点处的时候。 （Turbo C或Borland C用Turbo Debugger调试,Linux或Unix下用GDB调试时,看每句C对应的汇编并单步执行观察相应内存和寄存器变化。）  想要从本质上理解C指针，必须学习汇编以及C和汇编的对应关系。 从汇编的角度理解和学习C语言的指针，原本看似复杂的东西就会变得非常简单！ 指针即地址。“地址又是啥？”“只能从汇编语言和计算机组成原理的角度去解释了。” 但我又不得不承认：  有那么些人喜欢或者适合用“先具体再抽象”的方法学习和理解复杂事物；  而另一些人喜欢或者适合用“先抽象再具体”的方法学习和理解复杂事物。 而我本人属前者。  不要企图依赖输出指针相关表达式...的值【比如printf("%p\n",...);或者cout<<...】来理解指针的本质， 而要依赖调试时的反汇编窗口中的C/C++代码【比如void *p=(void *)(...);】及其对应汇编指令以及内存窗口中的内存地址和内存值来理解指针的本质。  这辈子不看内存地址和内存值；只画链表、指针示意图，画堆栈示意图，画各种示意图，甚至自己没画过而只看过书上的图……能从本质上理解指针、理解函数参数传递吗？本人深表怀疑！ 这辈子不种麦不收麦不将麦粒拿去磨面；只吃馒头、吃面条、吃面包、……甚至从没看过别人怎么蒸馒头，压面条，烤面包，……能从本质上理解面粉、理解面食吗？本人深表怀疑！！  提醒： “学习用汇编语言写程序” 和 “VC调试(TC或BC用TD调试)时按Alt+8、Alt+7、Alt+6和Alt+5,打开汇编窗口、堆栈窗口、内存窗口和寄存器窗口看每句C对应的汇编、单步执行并观察相应堆栈、内存和寄存器变化，这样过一遍不就啥都明白了吗。 （Linux或Unix下可以在用GDB调试时,看每句C对应的汇编并单步执行观察相应内存和寄存器变化。） 想要从本质上理解C指针，必须学习C和汇编的对应关系。” 不是一回事！  不要迷信书、考题、老师、回帖； 要迷信CPU、编译器、调试器、运行结果。 并请结合“盲人摸太阳”和“驾船出海时一定只带一个指南针。”加以理解。 任何理论、权威、传说、真理、标准、解释、想象、知识……都比不上摆在眼前的事实！  有人说一套做一套，你相信他说的还是相信他做的？ 其实严格来说这个世界上古往今来所有人都是说一套做一套，不是吗？  不要写连自己也预测不了结果的代码！  电脑内存或文件内容只是一个一维二进制字节数组及其对应的二进制地址； 人脑才将电脑内存或文件内容中的这个一维二进制字节数组及其对应的二进制地址的某些部分看成是整数、有符号数/无符号数、浮点数、复数、英文字母、阿拉伯数字、中文/韩文/法文……字符/字符串、汇编指令、函数、函数参数、堆、栈、数组、指针、数组指针、指针数组、数组的数组、指针的指针、二维数组、字符点阵、字符笔画的坐标、黑白二值图片、灰度图片、彩色图片、录音、视频、指纹信息、身份证信息……  十字链表交换任意两个节点C源代码（C指针应用终极挑战）http://download.csdn.net/detail/zhao4zhong1/5532495

引用 70 楼 my_live_123 的回复:[quote=引用 69 楼 sholber 的回复:] [quote=引用 67 楼 my_live_123 的回复:] [quote=引用 63 楼 sholber 的回复:] [quote=引用 61 楼 my_live_123 的回复:] char a[]具有extern属性，因此它在告诉编译器，这个东西可能在别的编译单元里定义里，这里要引用进来，由于你这里是全局的，它会放到common段里，为其指定大小。但是在链接时候，没有找到，默认它要报告一个警告，不会报错！然后使用common里指定大小为其分配内存！  首先，朕要批评你。extern不是属性。我知道你想说，extern意味着外部链接，这是你看书看中毒了。不要以为一个标识符在声明时使用了extern就是外部链接的： static int x; void f (void) {      extern int x;     //x具有内部链接，而非外部！ }  其次，int a []具有外部链接属性，但它并非是告诉C的实现这个东西在其它转换单元里定义。它在COFF的哪个段里安放并不重要，一点也不重要。重要的是，如果你声明了一个标识符且它具有文件作用域但没有初始化器，C的实现会将它视为一个试探性的定义。如果同一个标识符的所有外部声明都是试探性定义，则它相当于在当前转换单元内存在一个该标识符的外部定义，且具有一个值为0的初始化器，且该标识符的类型是所有试探性定义的所声明类型的复合类型。也就是说，在当前转换单元里，相当于有一个： char a [] = {0}; [/quote] 不说属性，还真不好描述！但是你下文又整出来个“外部链接属性”，问问你，它属于“There are three kinds of linkage: external, internal, and none.”的哪一种呢？ 你只是把我的主旨用自己的语言描述了一遍  ”相当于“一句是不对的！如果相当于它会被扔到数据段而不是comm段，吆西  放在common段属于历史继承，来自于Fortran语言，为了解决某些链接问题！自行搜索！ [/quote]  连我都糊涂我们在讨论什么。所以只好把我的主旨说一下： 1，如果你说external就对了，说extern就错了； 2，就一般的讨论而言，我从来就不关心C程序编译之后是什么样子。[/quote]  好，讨论到此结束，结贴！！！[/quote]  不行，不行，我原准备盖到1000楼，这才哪到哪。不过你放心，我到时候给你的分比别人都多！嘎嘎~~至于赵4，我是不会给他分滴。

引用 69 楼 sholber 的回复:[quote=引用 67 楼 my_live_123 的回复:] [quote=引用 63 楼 sholber 的回复:] [quote=引用 61 楼 my_live_123 的回复:] char a[]具有extern属性，因此它在告诉编译器，这个东西可能在别的编译单元里定义里，这里要引用进来，由于你这里是全局的，它会放到common段里，为其指定大小。但是在链接时候，没有找到，默认它要报告一个警告，不会报错！然后使用common里指定大小为其分配内存！  首先，朕要批评你。extern不是属性。我知道你想说，extern意味着外部链接，这是你看书看中毒了。不要以为一个标识符在声明时使用了extern就是外部链接的： static int x; void f (void) {      extern int x;     //x具有内部链接，而非外部！ }  其次，int a []具有外部链接属性，但它并非是告诉C的实现这个东西在其它转换单元里定义。它在COFF的哪个段里安放并不重要，一点也不重要。重要的是，如果你声明了一个标识符且它具有文件作用域但没有初始化器，C的实现会将它视为一个试探性的定义。如果同一个标识符的所有外部声明都是试探性定义，则它相当于在当前转换单元内存在一个该标识符的外部定义，且具有一个值为0的初始化器，且该标识符的类型是所有试探性定义的所声明类型的复合类型。也就是说，在当前转换单元里，相当于有一个： char a [] = {0}; [/quote] 不说属性，还真不好描述！但是你下文又整出来个“外部链接属性”，问问你，它属于“There are three kinds of linkage: external, internal, and none.”的哪一种呢？ 你只是把我的主旨用自己的语言描述了一遍  ”相当于“一句是不对的！如果相当于它会被扔到数据段而不是comm段，吆西  放在common段属于历史继承，来自于Fortran语言，为了解决某些链接问题！自行搜索！ [/quote]  连我都糊涂我们在讨论什么。所以只好把我的主旨说一下： 1，如果你说external就对了，说extern就错了； 2，就一般的讨论而言，我从来就不关心C程序编译之后是什么样子。[/quote]  好，讨论到此结束，结贴！！！

引用 67 楼 my_live_123 的回复:[quote=引用 63 楼 sholber 的回复:] [quote=引用 61 楼 my_live_123 的回复:] char a[]具有extern属性，因此它在告诉编译器，这个东西可能在别的编译单元里定义里，这里要引用进来，由于你这里是全局的，它会放到common段里，为其指定大小。但是在链接时候，没有找到，默认它要报告一个警告，不会报错！然后使用common里指定大小为其分配内存！  首先，朕要批评你。extern不是属性。我知道你想说，extern意味着外部链接，这是你看书看中毒了。不要以为一个标识符在声明时使用了extern就是外部链接的： static int x; void f (void) {      extern int x;     //x具有内部链接，而非外部！ }  其次，int a []具有外部链接属性，但它并非是告诉C的实现这个东西在其它转换单元里定义。它在COFF的哪个段里安放并不重要，一点也不重要。重要的是，如果你声明了一个标识符且它具有文件作用域但没有初始化器，C的实现会将它视为一个试探性的定义。如果同一个标识符的所有外部声明都是试探性定义，则它相当于在当前转换单元内存在一个该标识符的外部定义，且具有一个值为0的初始化器，且该标识符的类型是所有试探性定义的所声明类型的复合类型。也就是说，在当前转换单元里，相当于有一个： char a [] = {0}; [/quote] 不说属性，还真不好描述！但是你下文又整出来个“外部链接属性”，问问你，它属于“There are three kinds of linkage: external, internal, and none.”的哪一种呢？ 你只是把我的主旨用自己的语言描述了一遍  ”相当于“一句是不对的！如果相当于它会被扔到数据段而不是comm段，吆西  放在common段属于历史继承，来自于Fortran语言，为了解决某些链接问题！自行搜索！ [/quote]  连我都糊涂我们在讨论什么。所以只好把我的主旨说一下： 1，如果你说external就对了，说extern就错了； 2，就一般的讨论而言，我从来就不关心C程序编译之后是什么样子。

引用 54 楼 sholber 的回复:struct t {_Alignas (double) unsigned char c;} t; 就是错的。但是在标准的其它部分，这个声明是对的。 所以说，赵老师你说的话全都等于没说，全是fart. 汉字定义了三个字“好”“嘛”“你”，你可以组合“你好嘛”“你嘛，好”“嘛你好”“好你嘛”等等，但是有意义的要靠双方达成共识！同理，C文法定义组合方式是无穷尽的（尤其递归文法），某些组合是否有意义，要靠标准指定或编译器的解释！此外，C标准也只是描述其一个普遍的子集也不是全部！

引用 63 楼 sholber 的回复:[quote=引用 61 楼 my_live_123 的回复:] char a[]具有extern属性，因此它在告诉编译器，这个东西可能在别的编译单元里定义里，这里要引用进来，由于你这里是全局的，它会放到common段里，为其指定大小。但是在链接时候，没有找到，默认它要报告一个警告，不会报错！然后使用common里指定大小为其分配内存！  首先，朕要批评你。extern不是属性。我知道你想说，extern意味着外部链接，这是你看书看中毒了。不要以为一个标识符在声明时使用了extern就是外部链接的： static int x; void f (void) {      extern int x;     //x具有内部链接，而非外部！ }  其次，int a []具有外部链接属性，但它并非是告诉C的实现这个东西在其它转换单元里定义。它在COFF的哪个段里安放并不重要，一点也不重要。重要的是，如果你声明了一个标识符且它具有文件作用域但没有初始化器，C的实现会将它视为一个试探性的定义。如果同一个标识符的所有外部声明都是试探性定义，则它相当于在当前转换单元内存在一个该标识符的外部定义，且具有一个值为0的初始化器，且该标识符的类型是所有试探性定义的所声明类型的复合类型。也就是说，在当前转换单元里，相当于有一个： char a [] = {0}; [/quote] 不说属性，还真不好描述！但是你下文又整出来个“外部链接属性”，问问你，它属于“There are three kinds of linkage: external, internal, and none.”的哪一种呢？ 你只是把我的主旨用自己的语言描述了一遍  ”相当于“一句是不对的！如果相当于它会被扔到数据段而不是comm段，吆西  放在common段属于历史继承，来自于Fortran语言，为了解决某些链接问题！自行搜索！

大家都好厉害，想你们看齐

看讨论修行

引用 77 楼 zhao4zhong1 的回复:[quote=引用 76 楼 xionggch 的回复:] [quote=引用 14 楼 bear234 的回复:] 楼主你确定你这能编译通过？？？？？  我在gcc上编译报错了： error: storage size of 'c' isn't known. 我用了快20年V6了[/quote] 这个手势是6+1不是6[/quote]  不对。没看一上一下的么。应该是6-1=5或者6+1=7。向上的时候是7，向下的时候是5。

引用 76 楼 xionggch 的回复:[quote=引用 14 楼 bear234 的回复:] 楼主你确定你这能编译通过？？？？？  我在gcc上编译报错了： error: storage size of 'c' isn't known. 我用了快20年V6了[/quote] 这个手势是6+1不是6

引用 14 楼 bear234 的回复:楼主你确定你这能编译通过？？？？？  我在gcc上编译报错了： error: storage size of 'c' isn't known. 我用了快20年V6了

引用 74 楼 zhao4zhong1 的回复:1分也是分啊！ 赵4，你天天上班就水论坛了，CSDN公司的吗？

1分也是分啊！

最后，尽管C的实现会这么做，那也只是另外一回事。你说那个放在COMM段也没有意义，也是另一回事，C中的很多东西只从语法语义来解释足够了，不要言必称底层。回到正题，char a [] = 0是C的实现在编译程序时假定的，真实的情况是，a在转换单元内依然是不完整类型，编译器发出一个警告那还是轻的，它完全可以拒绝继续编译。

引用 61 楼 my_live_123 的回复:char a[]具有extern属性，因此它在告诉编译器，这个东西可能在别的编译单元里定义里，这里要引用进来，由于你这里是全局的，它会放到common段里，为其指定大小。但是在链接时候，没有找到，默认它要报告一个警告，不会报错！然后使用common里指定大小为其分配内存！  首先，朕要批评你。extern不是属性。我知道你想说，extern意味着外部链接，这是你看书看中毒了。不要以为一个标识符在声明时使用了extern就是外部链接的： static int x; void f (void) {      extern int x;     //x具有内部链接，而非外部！ }  其次，int a []具有外部链接属性，但它并非是告诉C的实现这个东西在其它转换单元里定义。它在COFF的哪个段里安放并不重要，一点也不重要。重要的是，如果你声明了一个标识符且它具有文件作用域但没有初始化器，C的实现会将它视为一个试探性的定义。如果同一个标识符的所有外部声明都是试探性定义，则它相当于在当前转换单元内存在一个该标识符的外部定义，且具有一个值为0的初始化器，且该标识符的类型是所有试探性定义的所声明类型的复合类型。也就是说，在当前转换单元里，相当于有一个： char a [] = {0};

回复错帖子了


Question: 帮我看看这代码什么问题，题目是利用KMP算法搜索一个TXT文档里的数据

在线着急等！！！

什么问题？

测试驱动

你要说明你的算法出了什么问题, 或者报了什么错才行,   其他人才好帮助你.  1. 调试看文件读取完成后, 文件内容是否都读取到. 2. 确认你的KMP算法工作正常, 即写一段代码来验证你的KMP能正常的匹配串.


Question: 这种情况是什么原因造成的

看着颜色像是ubuntu， 这里的原因是“宏中遇到#或##时就不会再展开宏中嵌套的宏了”。 就这么一规则，不要想太多，知道即可。

引用 3 楼 zhao4zhong1 的回复:宏展开时： 如果宏定义以#开头，不展开参数，直接替换。 故g(f(1,2))--->#f(1,2)--->"f(1,2)"； 如果宏定义不以#开头，展开参数，直接替换，由外层向里层，如果碰到的是#开头的宏，不继续往里层展开，往外层展开。 由外层向里层，如果碰到的是以非#开头的宏，继续往里层走，直至最里层，开始一层层往外层展开。 故h(f(1,2))--->h(12)--->g(12)---->#12----->"12"。    理解赵老师的意思  从外往里逐一看每个宏，直到当前的是#开头的，开始返回往外展开。 嵌套的宏定义不算#开头 exp：g(a)是#开头，而h(a)不是

#与##在宏定义中的--宏展开 #include <stdio.h> #define f(a,b) a##b #define g(a)   #a #define h(a) g(a) int main() {         printf("%s\n", h(f(1,2)));   // 12         printf("%s\n", g(f(1,2))); // f(1,2)         return 0; } 宏展开时： 如果宏定义以#开头，不展开参数，直接替换。 故g(f(1,2))--->#f(1,2)--->"f(1,2)"； 如果宏定义不以#开头，展开参数，直接替换，由外层向里层，如果碰到的是#开头的宏，不继续往里层展开，往外层展开。 由外层向里层，如果碰到的是以非#开头的宏，继续往里层走，直至最里层，开始一层层往外层展开。 故h(f(1,2))--->h(12)--->g(12)---->#12----->"12"。 PS： ##在宏中定义，是字符连接符 如a##b##c 等同于 "abc" #在宏开头出现，是表示宏展开的方式不同 #a 等同于"a" #abc 等同于 "abc" 复杂的: #include <stdio.h> #define f(a,b) a##b #define g(a)   #a #define h(a) g(a) int main() {         char a = 'a';         cout<<g(a)<<endl; // a         cout<<g(g(a))<<endl; // a         printf("%s\n", h(f(1,2)));   // 12         printf("%s\n", g(f(1,2))); // f(1,2)         printf("%s\n", g(h(f(1,2)))); // h(f(1,2))         printf("%s\n", h(g(f(1,2)))); // "f(1,2)"         printf("%s\n", h(h(f(1,2)))); // "12"         system("pause");         return 0; } 预处理后的：（在编译选项中添加/EP /P后编译生成的.i文件。gcc加-E） int main() {         char a = 'a';         cout<<"a"<<endl;         cout<<"g(a)"<<endl;         printf("%s\n", "12");         printf("%s\n", "f(1,2)");         printf("%s\n", "h(f(1,2))");         printf("%s\n", "\"f(1,2)\"");         printf("%s\n", "\"12\"");         system("pause");         return 0; } --------------------------------------------------- 宏解析 1.       ##操作符 ##操作符它的作用是在替代表中将其前后的参数连接成为一个预处理符号，它不能出现于宏替代表的开端和末尾。 例： #define concat(s,t) s##t #define AAA ABC concat(A, AA) 将被替换成 ABC 2.       重新扫描和替换 在替换列表中的所有参数替换过之后，预处理器将对结果token序列重新扫描以便对其中的宏再次替换。 当正在替换的宏在其替换列表中发现自身时，就不再对其进行替换。在任何正在嵌套替换的宏的替换过程中遇到正被替换的宏就对其不再进行替换（防止递归）。 例： #define ROOT AAA CCC #define AAA ROOT ROOT 将被替换成 ROOT CCC

我再加两个，好好感受一下：  printf("%s\n", h(g(f(1, 2)))); printf("%s\n", g(f(g(1), g(2))));


Question: 关于汽车倒车雷达——超声波测距的问题

这个涉及的面应该在：嵌入式开发，APP开发！


Question: 自定义函数与系统函数同名不报错，为什么？

引用 11 楼 a3192048 的回复:double fabs(double x)    //绝对值函数，这个函数与math.h中的fabs函数同名 {     if(x >= 0.0)         return x;     else         return -x; } 修改为： int fabs(double x)    //绝对值函数，这个函数与math.h中的fabs函数同名 {     if(x >= 0.0)         return x;     else         return -x; } 你用C编译器就会编译报错了。 用户可以重新定义标准库函数，若重新定义，该函数将失去原有含义。 但定义必须和math.h中声明保持一致。

函数库的基本原则，用户函数优先。

函数sqrt和fabs跟函数main在同一个模块，在链接阶段，会优先选择同一个模块内的符号，sqrt和fabs会当作是指令段（.text）中的已定义的全局符号，相当于是静态链接这些函数名。#include <math.h>不会起作用。 模块中不定义sqrt和fabs时，sqrt会作为未定义的全局符号，在执行阶段被动态链接到模块中，#include <math.h>就起到了声明作用。

我忘了是在哪儿看到了，只是记得有这么回事，现在用度娘找到下面的网址，你可以看一下答案和解析： http://www.ppkao.com/shiti/38173/

引用系统允许用户重新定义标准库函数，但此时该函数将失去原有含义。  To Turntogo: 讲得有道理，请问有出处吗？

用户调用标准库函数前不必重新定义，而只需使用预编译命令将该函数所在文件包括到用户源文件中即可。而且，系统允许用户重新定义标准库函数，但此时该函数将失去原有含义。

记得C语言有一个规定，就是允许用户自己编写与库函数同名的函数。

to Saleayas:  //  test.c #include<stdio.h> #include<math.h>  /* double fabs(double x)	//绝对值函数，这个函数与math.h中的fabs函数同名 { 	if(x >= 0.0) 		return x; 	else 		return -x; } */  double sqrt(double x)	//开平方函数，这个函数与math.h中的sqrt函数同名 { 	double x1, x2; 	x1 = x/2.0; 	x2 = (x1 + x/x1)/2.0; 	while(fabs(x2-x1)>1e-6) 	{ 		x1 = x2; 		x2 = (x1 + x/x1)/2.0; 	} 	return x1; }  int main() { 	double x = 3.0; 	printf("%.6lf\n", sqrt(x)); 	return 0; }   仍然能成功运行。也就是fabs函数来自math库，sqrt来自自定义函数，怎么就不冲突呢？   to mymtom: 有点感觉，但不太理解。   to focuslight: 函数原型是相同的，这一次的程序也修改了参数。 C语言有名字空间吗？

这要看链接是导入那个库。 你试试关掉一个函数试试。

math.h 里只是声明了fabs和sqrt函数，函数实现可以是数学库里的代码，也可以自己实现。

参数不同,   或者在不同名字空间下


Question: 求教~为什么变量重复定义vc报错而有的编译器不报错

谢谢，谢谢，大概明白了

VC6报错是因为， VC6中的语法不支持在for中声明变量，而应该这样  int i;   //先声明，再使用 for(i=1;;);   建议在C中遵守上述语法，而在C++都可以。

凡是人造的东西都有缺陷，编译器也是人编的。

vc++6.0出错-error C2086: 'a' : redefinition  这个重定义，应该可以看出来，将a当成了函数的局部变量。 以前我用过一个编译器，对于c语言，在函数中的所有局部变量，都要在开始出全部声明/定义好，在中间就出错。 这个是编译器问题，推荐用gcc吧，可以对编译选项有个比较透彻的理解和使用。

引用 4 楼 mymtom 的回复:vc++6.0对C++的支持有限  支持  对于表达式int a = ++n + ++n + ++n，vc6.0就计算错误。

各个编译器默认的标准不一样，gnu好像不支持这种语法，c99标准就可以

引用 5 楼 Minikinfish 的回复:[quote=引用 4 楼 mymtom 的回复:] vc++6.0对C++的支持有限  支持  对于表达式int a = ++n + ++n + ++n，vc6.0就计算错误。[/quote]  支持一半  int a = ++n + ++n + ++n 这个不应该算编译器的bug，应该算程序员的bug

它报错你就不那样写就行了嘛。。。纠结这个没什么用


Question: C语言编程

引用 2 楼 zhao4zhong1 的回复:[quote=引用 1 楼 zhangxiangDavaid 的回复:] 重心法解模糊 C语言 http://www.baigoogledu.com/s.php?hl=zh-CN&q=%D6%D8%D0%C4%B7%A8%BD%E2%C4%A3%BA%FD+C%D3%EF%D1%D4 欢迎现学现卖！[/quote] 大牛，可不要嘲笑晚辈啊

引用 1 楼 zhangxiangDavaid 的回复:重心法解模糊 C语言 http://www.baigoogledu.com/s.php?hl=zh-CN&q=%D6%D8%D0%C4%B7%A8%BD%E2%C4%A3%BA%FD+C%D3%EF%D1%D4 欢迎现学现卖！


Question: C语言库里有数据结构的算法吗

基本没有，C语言要用比较复杂的数据结构，比如链表什么的一般是自己写的逻辑。 当然可以从网上找一些比较成熟的源代码来用。

C++里有STL

标准C中个两个算法:bsearch与qsort

数据结构的算法? 算法是算法，数据结构是数据结构，这两个不一样的。 不过无论你要什么c里面都没有的。  不过c++里的STL库提供的一些数据结构，比如队列，栈，链表，红黑二叉树什么的，你搜搜STL就知道了。

有两个，但是不常用，建议使用C++的STL

引用 2 楼 mewiteor 的回复:标准C中个两个算法:bsearch与qsort 英雄所见略同


Question: 关于结构体内存问题

１:数据成员对齐规则：结构(struct)(或联合(union))的数据成员，第一个数据成员放在offset为0的地方，以后每个数据成员存储的起始位置要从该成员大小或者成员的子成员大小（只要该成员有子成员，比如说是数组，结构体等）的整数倍开始(比如int在３２位机为４字节,则要从４的整数倍地址开始存储。     ２:结构体作为成员:如果一个结构里有某些结构体成员,则结构体成员要从其内部最大元素大小的整数倍地址开始存储.(struct a里存有struct b,b里有char,int ,double等元素,那b应该从8的整数倍开始存储.)     ３:收尾工作:结构体的总大小,也就是sizeof的结果,.必须是其内部最大成员的整数倍.不足的要补齐.

仅供参考：#include <stdio.h> #define field_offset(s,f) (int)(&(((struct s *)(0))->f)) struct AD  { int a; char b[13]; double c;}; #pragma pack(push) #pragma pack(1) struct A1  { int a; char b[13]; double c;}; #pragma pack(2) struct A2  { int a; char b[13]; double c;}; #pragma pack(4) struct A4  { int a; char b[13]; double c;}; #pragma pack(8) struct A8  { int a; char b[13]; double c;}; #pragma pack(16) struct A16 { int a; char b[13]; double c;}; #pragma pack(pop) int main() {     printf("AD.a %d\n",field_offset(AD,a));     printf("AD.b %d\n",field_offset(AD,b));     printf("AD.c %d\n",field_offset(AD,c));     printf("\n");     printf("A1.a %d\n",field_offset(A1,a));     printf("A1.b %d\n",field_offset(A1,b));     printf("A1.c %d\n",field_offset(A1,c));     printf("\n");     printf("A2.a %d\n",field_offset(A2,a));     printf("A2.b %d\n",field_offset(A2,b));     printf("A2.c %d\n",field_offset(A2,c));     printf("\n");     printf("A4.a %d\n",field_offset(A4,a));     printf("A4.b %d\n",field_offset(A4,b));     printf("A4.c %d\n",field_offset(A4,c));     printf("\n");     printf("A8.a %d\n",field_offset(A8,a));     printf("A8.b %d\n",field_offset(A8,b));     printf("A8.c %d\n",field_offset(A8,c));     printf("\n");     printf("A16.a %d\n",field_offset(A16,a));     printf("A16.b %d\n",field_offset(A16,b));     printf("A16.c %d\n",field_offset(A16,c));     printf("\n");     return 0; } //AD.a 0 //AD.b 4 //AD.c 24 // //A1.a 0 //A1.b 4 //A1.c 17 // //A2.a 0 //A2.b 4 //A2.c 18 // //A4.a 0 //A4.b 4 //A4.c 20 // //A8.a 0 //A8.b 4 //A8.c 24 // //A16.a 0 //A16.b 4 //A16.c 24 // //

有一句话没看太懂： “又不是共用体的各成员共享一段内存”  不管这句话了。 这个问题还比较基本的。涉及到了一个字节对齐的问题。  上面已经有仁兄提到了，这个还是要看你的编译器使用的对齐方式，当然这个对齐方式也可以自己设置。 大部分编译器默认的都是4字节对齐，如果是4字节对齐的话，上面两个结构体的大小都是16。（其中char类型补齐4字节）。 如果设置8字节对齐，就如你所说的，第一个大小为16（8+8），其中x和y共同占用8个字节，第二个为24（8+8+8），x和z分别占8个字节。  另外，提一点，在实际中，测试发现，字节的对齐方式应该与机器的位数有一定的关系的。 环境 linux、g++编译器 32位系统上（默认4字节对齐），最大是4字节对齐 64未系统上（默认8字节对齐），最大是8字节对齐 设置过大的话，是无效的，编译器还是默认对齐进行编译。   ------------------------- 个人见解，共同学习。

数据成员对齐 必须不一样 第一个16 第二个24  最长的是double 8所以规格是8  第一个就是 xxxx y- - - zzzz zzzz  第二个就是 xxxx- - - - yyyyyyyy z--- - - - -

在C和C++中成员变量的声明顺序和它在内存中的位置的前后关系是一致的，但不一定连续存储，还要考虑字节对齐的问题，以及C++中的对多态的支持，而添加的多余数据类型。

#include "stdafx.h"  struct node1 {     int x;     char y;     double z; };  struct node2 {     int x;     double z;     char y; };  int main() {     int n1 = sizeof(node1);     int n2 = sizeof(node2);      return 0; }  断点时局部变量值： 		n2	24	int 		n1	16	int  原来我也理解错了，第二种定义方式按8字节对齐了

你的理解可以说对了一半，你还得看编译器的默认对齐大小 在我以往的编程经验里，vs2005和我现在在用的vs2010，默认对齐大小是4字节 所以你的结构体如果放到我的编译器中的话，两个结构的大小都是一样的16字节  第一个 int 占4字节，第二个 char 占1字节，编译器按默认4字节对齐自动补齐变为4字节，第三个 double 占8字节，是4字节的整数倍，不用补齐，所以合共大小是16字节  第二种定义方式原理一样，所以结果也是16字节大小

每个单元多大取决于结构体中最大基本类型的大小。 那么 这俩个结构体每个单元最大都是double类型 16个字节 对于第一个 第一个单元可以存放int和char 第二个单元存放double 这样就是16*2=32字节 对于第二个 第一个单元存放int后 剩下不够double 所以有第二个单元全是double 无剩余 所以需要第三个单元 这样就是 16*3=48字节

已找到 还是应该自己先想办法


Question: 这段代码运行时为什么出问题？？

虽然定义了指针，但是这个指针没有指向某个特定的地址，因此赋值是会出错的

指针不分配内存就用，厉害啊

先把指针 malloc 一下，就好了

老总说，给你一个团队，你干吧，...... 你就是那个a,那个团队呢？

a指针 是所谓的 野指针，也就是说a指向的地方是没有预告分配的  你可以为a分配一片内存，如 int* a = new int[10]; 也可以让a等于某个分配好的内存地址，如int b[10]; int *a = b;

其实电脑开机后物理内存的每个字节都是可读写的，从来不会因为所谓的new、delete或malloc、free而被创建、销毁。区别仅在于操作系统内存管理模块在你读写时是否能发现并是否采取相应动作而已。操作系统管理内存的粒度不是字节而是页，一页通常为4KB。

打个比方说，你朝着一大堆人扔了一块石头，你还在问，为什么有人受伤了？ 其实，有人受伤了是必然的，没有人受伤的机率是非常小的的。 就像你的这个问题，典型的野指针的问题，出问题是必然的，不出问题的机率是非常小的。

修改如下：  #include <stdio.h> #include <stdlib.h> int main(void) { 	int *a = malloc(sizeof(int)*3);  //为a分配空间(让a指向一片可用的内存) 	int i; 	for (i = 0; i<3; i++) 	{ 		*(a + i) = i; 	} 	for (i = 0; i<3; i++) 	{ 		printf("%d\n", a[i]); 	} 	free(a);   //释放内存 	return 0; } //0 //1 //2

有个野指针啊

指针变量a没有赋值，没有指向一个具体的地址，所以*(a+i)就无法寻址到一个具体储存单元，所以*(a+i)=i错误

我再补充一下，例如这样就可以，我把你的程序改了一点 #include <stdio.h> #include <stdlib.h> int main(void)  { 	int b[3]; 	int *a; 	int i; 	a=b; 	for(i=0;i<3;i++) 	{ 		*(a+i)=i; 	} 	for(i=0;i<3;i++) 	{ 		printf("%d\n",*(a+i)); 	} 	return 0; }

指针变量的赋值错误，*a是a所指向的变量，因为a在定义时并无确定的值，所以*a的值也是不确定的，在运行程序时会出现不可知的错误

我自问后感觉。。。a是一个int型的指针变量呀。

很明显是指针未定义 你自问一下，代码中的 a 是什么？它又代表了什么？


Question: 简单编程

int main(void) { 	int s, n; 	s = 0; 	n = 0; 	while (s <= 100) 	{ 		n += 1; 		s += n; 	} 	s -= n; 	n--; 	printf("n=%d,s=%d\n", n, s);  //n=13,s=91 	return 0; }


Question: 求助字符转整形个问题

大头 小头 存储  http://blog.csdn.net/zjf82031913/article/details/7245183


Question: 菜鸟求大神帮看代码哪里有错

引用 1 楼 mscf 的回复:循环逻辑不对，第一次循环结束后p为空了，你访问它的所指成员是有问题的~ 嗯呐！是的！现在我明白了！谢谢啦！

引用 3 楼 zhangxiangDavaid 的回复:修改如下：  #include <stdio.h> #include <stdlib.h> #define LEN sizeof(struct student) struct student    //定义学生链表结点类型 { 	long ID;//学号 	char name[12];//姓名 	char sex[3];//性别 	int age;//年龄 	struct student *next; }; int n; /************************ 函数功能：创建队列式链表 函数参数：无 函数返回值：头指针head *************************/ struct student *create() { 	struct student *head, *p, *last; 	int i; 	head = (struct student*)malloc(LEN);//创建头结点 	//printf("请依次输入每一个学生的学号、姓名、性别、年龄：\n"); 	//scanf_s("%d", &head->ID);//输入学号 	//getchar(); 	//gets_s(head->name, 12);//输入姓名 	//gets_s(head->sex, 3);//输入性别 	//scanf_s("%d", &head->age);//输入年龄 	last = head;//末结点指针last初始化 	for (i = 0; i < n; i++) 	{ 		p = (struct student *)malloc(LEN);//创建新结点 		printf("请依次输入学生%2d的学号、姓名、性别、年龄：\n", i); 		scanf_s("%d", &p->ID);//输入学号 		getchar(); 		gets_s(p->name, 12);//输入姓名 		gets_s(p->sex, 3);//输入性别 		scanf_s("%d", &p->age);//输入年龄 		last->next = p;//插入链尾 		last = last->next;//last指针后移至末结点 	} 	last->next = NULL;//链表终止延伸 	return head;//返回头指针 } /****************************** 函数功能：打印学生链表中的数据 函数参数：头指针head 函数返回值：无 *******************************/ void printlist(struct student *head) { 	struct student *p; 	//p = head;//指向头结点 	p = head->next;   //指向第一个节点 	printf("学生数据为：\n"); 	while (p != NULL) 	{ 		printf("%ld %s %s %d\n", p->ID, p->name, p->sex, p->age);//输出当前结点包含的信息 		p = p->next;//指向下一个结点	 	} } /************************************************** 函数功能：删除含有年龄等于输入年龄的结点 函数参数：头指针head；整形变量key，储存输入的年龄 函数返回值：头指针head **************************************************/ struct student *del(struct student*head) { 	struct student *p, *pre; 	int i, key; 	//pre = p = head; 	pre = head; 	p = head->next; 	if (NULL == p) 	{ 		printf("空链表无法删除\n"); 		return head; 	} 	printf("请输入要删除的年龄："); 	scanf_s("%d", &key); 	//for (i = 0; i < n; i++) 	while(p) 	{ 		while (key != p->age && p->next != NULL) 		{ 			pre = p; 			p = p->next; 		}  		if (p->age == key) 		{ 			/*  既然是带了头节点，就不需要这样操作了 			if (p == head) 				head = head->next; 			else 				pre->next = p->next; 				*/ 			pre->next = p->next;   //只用这一句就行 			free(p); 			p = pre->next; 		} 		else 		{ 			printf("不存在年龄为%d的学生", key); 			break; 		} 	} 	return head;//返回节点删除以后的链表的头指针 } int main() { 	struct student *head; 	printf("请输入学生数：\n"); 	scanf_s("%d", &n); 	head = create(); 	printlist(head); 	head = del(head); 	printlist(head); 	printf("\nmission has been completed!\n"); 	getchar(); 	getchar(); 	return 0; }  多谢大神，终于知道错在哪里啦！！问题已解决

p指针为空了

运行：

for循环纯粹多余，通过单项链表的指针迭代就能控制循环~

循环逻辑不对，第一次循环结束后p为空了，你访问它的所指成员是有问题的~


Question: C语言读写文件求助

fopen, _wfopen Open a file.  FILE *fopen( const char *filename, const char *mode );  FILE *_wfopen( const wchar_t *filename, const wchar_t *mode );  Function Required Header Compatibility  fopen <stdio.h> ANSI, Win 95, Win NT  _wfopen <stdio.h> or <wchar.h> Win NT    For additional compatibility information, see Compatibility in the Introduction.  Libraries  LIBC.LIB Single thread static library, retail version  LIBCMT.LIB Multithread static library, retail version  MSVCRT.LIB Import library for MSVCRT.DLL, retail version    The c, n, and t mode options are Microsoft extensions for fopen and _fdopen and should not be used where ANSI portability is desired.  Return Value  Each of these functions returns a pointer to the open file. A null pointer value indicates an error.   Parameters  filename  Filename  mode  Type of access permitted  Remarks  The fopen function opens the file specified by filename. _wfopen is a wide-character version of fopen; the arguments to _wfopen are wide-character strings. _wfopen and fopen behave identically otherwise.  Generic-Text Routine Mappings  TCHAR.H Routine  _UNICODE & _MBCS Not Defined _MBCS Defined _UNICODE Defined  _tfopen fopen fopen _wfopen    The character string mode specifies the type of access requested for the file, as follows:  "r"  Opens for reading. If the file does not exist or cannot be found, the fopen call fails.  "w"  Opens an empty file for writing. If the given file exists, its contents are destroyed.  "a"  Opens for writing at the end of the file (appending) without removing the EOF marker before writing new data to the file; creates the file first if it doesn’t exist.  "r+"  Opens for both reading and writing. (The file must exist.)  "w+"  Opens an empty file for both reading and writing. If the given file exists, its contents are destroyed.  "a+"  Opens for reading and appending; the appending operation includes the removal of the EOF marker before new data is written to the file and the EOF marker is restored after writing is complete; creates the file first if it doesn’t exist.  When a file is opened with the "a" or "a+" access type, all write operations occur at the end of the file. The file pointer can be repositioned using fseek or rewind, but is always moved back to the end of the file before any write operation is carried out. Thus, existing data cannot be overwritten.  The "a" mode does not remove the EOF marker before appending to the file. After appending has occurred, the MS-DOS TYPE command only shows data up to the original EOF marker and not any data appended to the file. The "a+" mode does remove the EOF marker before appending to the file. After appending, the MS-DOS TYPE command shows all data in the file. The "a+" mode is required for appending to a stream file that is terminated with the CTRL+Z EOF marker.  When the "r+", "w+", or "a+" access type is specified, both reading and writing are allowed (the file is said to be open for “update”). However, when you switch between reading and writing, there must be an intervening fflush, fsetpos, fseek, or rewind operation. The current position can be specified for the fsetpos or fseek operation, if desired.   In addition to the above values, the following characters can be included in mode to specify the translation mode for newline characters:  t  Open in text (translated) mode. In this mode, CTRL+Z is interpreted as an end-of-file character on input. In files opened for reading/writing with "a+", fopen checks for a CTRL+Z at the end of the file and removes it, if possible. This is done because using fseek and ftell to move within a file that ends with a CTRL+Z, may cause fseek to behave improperly near the end of the file.   Also, in text mode, carriage return–linefeed combinations are translated into single linefeeds on input, and linefeed characters are translated to carriage return–linefeed combinations on output. When a Unicode stream-I/O function operates in text mode (the default), the source or destination stream is assumed to be a sequence of multibyte characters. Therefore, the Unicode stream-input functions convert multibyte characters to wide characters (as if by a call to the mbtowc function). For the same reason, the Unicode stream-output functions convert wide characters to multibyte characters (as if by a call to the wctomb function).  b  Open in binary (untranslated) mode; translations involving carriage-return and linefeed characters are suppressed.   If t or b is not given in mode, the default translation mode is defined by the global variable _fmode. If t or b is prefixed to the argument, the function fails and returns NULL.   For more information about using text and binary modes in Unicode and multibyte stream-I/O, see Text and Binary Mode File I/O and Unicode Stream I/O in Text and Binary Modes.  c  Enable the commit flag for the associated filename so that the contents of the file buffer are written directly to disk if either fflush or _flushall is called.  n  Reset the commit flag for the associated filename to “no-commit.” This is the default. It also overrides the global commit flag if you link your program with COMMODE.OBJ. The global commit flag default is “no-commit” unless you explicitly link your program with COMMODE.OBJ.  Valid characters for the mode string used in fopen and _fdopen correspond to oflag arguments used in _open and _sopen, as follows.  Characters in mode String Equivalent oflag Value for _open/_sopen   a _O_WRONLY | _O_APPEND (usually _O_WRONLY | _O_CREAT | _O_APPEND)  a+ _O_RDWR | _O_APPEND (usually _O_RDWR | _O_APPEND | _O_CREAT )  r _O_RDONLY  r+ _O_RDWR  w _O_WRONLY (usually _O_WRONLY | _O_CREAT | _O_TRUNC)  w+ _O_RDWR (usually _O_RDWR | _O_CREAT | _O_TRUNC)  b _O_BINARY  t _O_TEXT  c None  n None    Example  /* FOPEN.C: This program opens files named "data"  * and "data2".It  uses fclose to close "data" and  * _fcloseall to close all remaining files.  */  #include <stdio.h>  FILE *stream, *stream2;  void main( void ) {    int numclosed;     /* Open for read (will fail if file "data" does not exist) */    if( (stream  = fopen( "data", "r" )) == NULL )       printf( "The file 'data' was not opened\n" );    else       printf( "The file 'data' was opened\n" );     /* Open for write */    if( (stream2 = fopen( "data2", "w+" )) == NULL )       printf( "The file 'data2' was not opened\n" );    else       printf( "The file 'data2' was opened\n" );     /* Close stream */    if( fclose( stream ) )       printf( "The file 'data' was not closed\n" );     /* All other files are closed: */    numclosed = _fcloseall( );    printf( "Number of files closed by _fcloseall: %u\n", numclosed ); }   Output  The file 'data' was opened The file 'data2' was opened Number of files closed by _fcloseall: 1   Stream I/O Routines  See Also   fclose, _fdopen, ferror, _fileno, freopen, _open, _setmode

修改如下：  if (fgets(buff, 1024, p2) != NULL)            //检查能否读取数据 { 	fseek(p2, 32L + i * 8, 0);          //主要对这句，进行修改 	fputs(read_fpxxfpje, p2); 	//fseek(p2, 109L, 1);   //这句没看出有什么作用 }


Question: 如何避免野指针

判断指针是否有效  http://blog.csdn.net/qq_34453988/article/details/50997112

1、定义的时候就立即赋值 2、不需要的时候，立即置空=NULL 3、尽量压缩生命周期，可以利用do while(0)等屏蔽后面不需要的变量

这是都是简单的编码问题，提高下编码的认真度，可以省掉很多这样的冗余代码。

指针初始化 p = NULL; 用完之后 p = NULL;  指针用之前需测试其有效性，如： if(p != NULL) {   //... }

一般fclose后，此文件已经不再使用。用户有责任维护自己代码的安全性。置空与否，看其他地方是否重复使用，识情况而定！

fclose(f);    //之后，f的值仍是原值，没有清零。故， f=NULL; 若再次使用f，编译器就会提示错误。

请牢记：源代码本身的书写是否结构化或面向对象或符合设计模式或敏捷…并不重要，重要的是你是否使用结构化或面向对象或符合设计模式或敏捷…的方法命名标识符、阅读、修改、检查、测试源代码。  意思是你程序结构看上去再合理，再简洁，也不一定比看上去一团乱麻的程序结构在运行或修改时更不易出错，更方便修改，出错了更容易找到哪里出错和具体出错的原因，更容易改正错误。  试对比 图书馆（对图书的分类够结构化了吧） 和 搜索引擎（可看作是扁平化任何结构数据，仅支持全文检索） 哪个处理信息更方便、更高效。  所以 与其费劲去重构代码让其看上去更简洁、更合理 不如费劲学习grep、sed、awk、……这类全文搜索和批处理编辑的工具。  结构越复杂，越难修改，越难除错。 有时（甚至大多数时候），看上去越合理、越简洁的代码，运行起来性能越差，出错时查找原因越难，找到出错原因后改正越费劲。  程序员要做的不是尽力避免错误，而是聚焦在快速发现并改正错误。真正以快速方式轻易解决错误，“快速的失败”远胜过“预防错误”。Fred George

如何避免寄信时被“查无此人”退回？

用智能指针。


Question: Win32，非模态对话框创建问题

引用 1 楼 zhao4zhong1 的回复:http://bbs.csdn.net/topics/390374955  我看过MSDN，但是我遇到的问题，无法用MSDN上的实例解决，您帮我看看，谢谢。 我现在需要直接加载RC资源中的对话框，因此 custommessage.commonvariables.hMainWnd = CreateDialog(custommessage.commonvariables.hInst, MAKEINTRESOURCE(IDD_DIALOG_WNDPROC), 0, (DLGPROC)WndProc);  在回掉函数WndProc中，点击高级搜索后弹出搜索的对话框， case IDB_WNDPROC_SEARCHALLDLGDOWN:                 {                     custommessage.commonvariables.hSearchWnd = CreateDialog(custommessage.commonvariables.hInst, MAKEINTRESOURCE(IDD_DIALOG_ALLSEARCH), 0, (DLGPROC)AllsearchProc);  // hWnd也不成                     ShowWindow(custommessage.commonvariables.hSearchWnd, SW_SHOW);                 }                 break;  其中AllsearchProc与WndProc所对应的两个对话框不是父子关系，而是同等关系。但是点击AllsearchProc中的关闭按钮、移动、点击搜索按钮 case IDB_SEARCH_ALLSEARCH:                 {                     DestroyWindow(hWnd);                     hWnd = NULL;                 }                 break;  都不响应消息。 而且我也用WM_SYSCOMMAND来实现关闭操作，仍然没反应。  case WM_SYSCOMMAND:         {             if(wParam == SC_CLOSE)             {                 DestroyWindow(hWnd);                 hWnd = NULL;             }         }         break;  不知道为什么.

引用 2 楼 Minikinfish 的回复:Windows程序很简单，就几点内容 1、窗口需要注册， 2、注册需要proc 3、proc需要循环泵的支持 4、大量窗口的api 5、SetWindowLong  WGL_DLGPROC 可以对窗体任意修改  这个我知道，我现在需要直接加载RC资源中的对话框，因此 custommessage.commonvariables.hMainWnd = CreateDialog(custommessage.commonvariables.hInst, MAKEINTRESOURCE(IDD_DIALOG_WNDPROC), 0, (DLGPROC)WndProc);  在回掉函数WndProc中，点击高级搜索后弹出搜索的对话框， case IDB_WNDPROC_SEARCHALLDLGDOWN:                 {                     custommessage.commonvariables.hSearchWnd = CreateDialog(custommessage.commonvariables.hInst, MAKEINTRESOURCE(IDD_DIALOG_ALLSEARCH), 0, (DLGPROC)AllsearchProc);  // hWnd也不成                     ShowWindow(custommessage.commonvariables.hSearchWnd, SW_SHOW);                 }                 break;  其中AllsearchProc与WndProc所对应的两个对话框不是父子关系，而是同等关系。但是点击AllsearchProc中的关闭按钮、移动、点击搜索按钮 case IDB_SEARCH_ALLSEARCH:                 {                     DestroyWindow(hWnd);                     hWnd = NULL;                 }                 break;  都不响应消息。 而且我也用WM_SYSCOMMAND来实现关闭操作，仍然没反应。  case WM_SYSCOMMAND:         {             if(wParam == SC_CLOSE)             {                 DestroyWindow(hWnd);                 hWnd = NULL;             }         }         break;  不知道为什么.


Question: 第二维已知的二维结构体数组内存问题

引用 1 楼 user-1 的回复:sizeof(XX*)明显就不对 我觉得应该是8就行吧，能正确打印结果。 那应该改成什么呢？

sizeof(XX*)明显就不对


Question: C 的(++j)+(++j) 为什么和php的结果不一样，j=1

引用 11 楼 zhao4zhong1 的回复:[quote=引用 9 楼 mymtom 的回复:] Undefined behavior 实在没有讨论的必要 闲来无事可以拿来练练嘴皮子。[/quote] 表情贴错了。

引用 9 楼 mymtom 的回复:Undefined behavior 实在没有讨论的必要 闲来无事可以拿来练练嘴皮子。

Undefined behavior 实在没有讨论的必要

为什么要和php的一样？php一个脚本语言，能和C++比？

考察表达式的值  	int i; 	int j = 1;  mov         dword ptr [ebp-14h],1   	i = (++j) + (++j);  mov         eax,dword ptr [ebp-14h]    add         eax,1    mov         dword ptr [ebp-14h],eax    mov         ecx,dword ptr [ebp-14h]    add         ecx,1    mov         dword ptr [ebp-14h],ecx    mov         edx,dword ptr [ebp-14h]    add         edx,dword ptr [ebp-14h]    mov         dword ptr [ebp-8],edx    这之后显然 i=6; 这是vs下的汇编，其它编译器，效果很可能不一样

引用 3 楼 zoen210 的回复:[quote=引用 1 楼 user-6 的回复:] 我可以发表一下自己的看法吗！？c中的答案应该是3  而php中应该是4  编译器的默认不同！我也是新手！回答不好的地方请谅解 c 答案是 6， php是5[/quote]C中这个表达式是错误的  具体可以参加置顶帖

这是vs的debug模式下的汇编代码：  	int j = 1;  mov         dword ptr [ebp-8],1   	(++j) + (++j);  mov         eax,dword ptr [ebp-8]    add         eax,1    mov         dword ptr [ebp-8],eax    mov         ecx,dword ptr [ebp-8]    add         ecx,1    mov         dword ptr [ebp-8],ecx    显然，之后j=3;

引用 1 楼 user-6 的回复:我可以发表一下自己的看法吗！？c中的答案应该是3  而php中应该是4  编译器的默认不同！我也是新手！回答不好的地方请谅解 c 答案是 6， php是5

你这最后输出问的是j的值吧


Question: 请教C语言一个问题

引用 2 楼 ma815841356 的回复:[quote=引用 1 楼 zhao4zhong1 的回复:] 没见题目中说数据肯定是正整数，也没见题目中说数据中没有小数。  你好，这道题目侧重点不是在数据类型上，刚刚受人点拨，原来按题目要求我还应该考虑长方体里面的切面，不能只单单考虑外面的切面，不过仍要感谢你的回复[/quote] 原来如此！

引用 1 楼 zhao4zhong1 的回复:没见题目中说数据肯定是正整数，也没见题目中说数据中没有小数。  你好，这道题目侧重点不是在数据类型上，刚刚受人点拨，原来按题目要求我还应该考虑长方体里面的切面，不能只单单考虑外面的切面，不过仍要感谢你的回复

没见题目中说数据肯定是正整数，也没见题目中说数据中没有小数。


Question: 请问各位大神如何知道c语言编译器如CodeC:Blocks运行一个程序时所用的时间和内存呢？

引用 5 楼 ma815841356 的回复:[quote=引用 3 楼 zhangxiangDavaid 的回复:] 运行时间可编写代码获得，内存的使用情况可使用工具，如VMMap  你好，我用的是CodeC:Blocks，每次程序运行完后都有在结尾显示运行时间，大致与你给的代码时间一致，但我提交代码到OJ后它显示的时间却跟我的不一样，而且相差很大，请问有没有办法在本地运行C语言程序时就知道代码提交到OJ后的时间？[/quote] 这个运行时间，跟系统有很大关系，只能用我给的代码大概测算下。

那说明你还有改进的空间

引用 3 楼 zhangxiangDavaid 的回复:运行时间可编写代码获得，内存的使用情况可使用工具，如VMMap  你好，我用的是CodeC:Blocks，每次程序运行完后都有在结尾显示运行时间，大致与你给的代码时间一致，但我提交代码到OJ后它显示的时间却跟我的不一样，而且相差很大，请问有没有办法在本地运行C语言程序时就知道代码提交到OJ后的时间？

可用以下代码获得程序运行的毫秒数：  #include <time.h> #include <windows.h> int main(void) { 	clock_t t1, t2; 	t1 = clock(); 	//do some work 	Sleep(2000); 	t2 = clock(); 	printf("%dms\n", t2 - t1); 	return 0; }

运行时间可编写代码获得，内存的使用情况可使用工具，如VMMap

VMMap 是进程虚拟和物理内存分析实用工具。http://technet.microsoft.com/zh-cn/sysinternals/dd535533

无profiler不要谈效率！！尤其在这个云计算、虚拟机、模拟器、CUDA、多核 、多级cache、指令流水线、多种存储介质、……满天飞的时代！


Question: c中格式输出的问题

这里的#是起到打印前缀0或者0x的作用，这里用的是8进制，所以会打印前缀0

引用 1 楼 zhangxiangDavaid 的回复:你在什么环境下打印的？我的输入和你不一样 输出

你在什么环境下打印的？我的输入和你不一样

在vc++6.0里运行的。3楼正解。谢谢！


Question: 如何根据pngdata的数组与长度，生成一个png文件

仅供参考：#include <math.h> #include <string.h> #include <stdio.h> #include <windows.h> #include <gdiplus.h> #pragma comment(lib, "gdiplus.lib") using namespace Gdiplus; wchar_t formats[5][11]={     L"image/bmp",     L"image/jpeg",     L"image/gif",     L"image/tiff",     L"image/png", }; wchar_t exts[5][5]={     L".bmp",     L".jpg",     L".gif",     L".tif",     L".png", }; int GetEncoderClsid(const WCHAR* format, CLSID* pClsid) {    UINT  num = 0;          // number of image encoders    UINT  size = 0;         // size of the image encoder array in bytes    ImageCodecInfo* pImageCodecInfo = NULL;    GetImageEncodersSize(&num, &size);    if(size == 0) return -1;  // Failure    pImageCodecInfo = (ImageCodecInfo*)(malloc(size));    if(pImageCodecInfo == NULL) return -1;  // Failure    GetImageEncoders(num, size, pImageCodecInfo);    for (UINT j = 0; j < num; ++j) {       if ( wcscmp(pImageCodecInfo[j].MimeType, format) == 0 ) {          *pClsid = pImageCodecInfo[j].Clsid;          free(pImageCodecInfo);          return j;  // Success       }    }    free(pImageCodecInfo);    return -1;  // Failure } int wmain(int argc,wchar_t *argv[]) {     int r=1;     if (argc<4) {     USAGE:         wprintf(L"%s srcimg.{bmp|jpg|gif|tif|png|wmf|emf|ico}  desimg.{bmp|jpg|gif|tif|png}  angle\n",argv[0]);         return r;     }     int i;     for (i=0;i<5;i++) {         if (0==_wcsicmp(argv[1]+wcslen(argv[1])-4,exts[i])) break;     }     if (i>=5) goto USAGE;     for (i=0;i<5;i++) {         if (0==_wcsicmp(argv[2]+wcslen(argv[2])-4,exts[i])) break;     }     if (i>=5) goto USAGE;     GdiplusStartupInput gdiplusstartupinput;     ULONG_PTR gdiplustoken;     GdiplusStartup(&gdiplustoken, &gdiplusstartupinput, NULL);     {         Image img(argv[1]);         if (Ok==img.GetLastStatus()) {             UINT height = img.GetHeight();             UINT width  = img.GetWidth();             REAL angle;             if (1==swscanf_s(argv[3],L"%f",&angle)) {                 REAL size;                 size=(REAL)sqrt(1.0*width*width+1.0*height*height);                 Matrix mat;                 mat.Translate(size / -2.0f, size / -2.0f);                 mat.Rotate(-angle, MatrixOrderAppend);                 mat.Translate(size / 2.0f, size / 2.0f, MatrixOrderAppend);                 PointF pfTL((size-width)/2.0f      ,(size-height)/2.0f       );                 PointF pfTR((size-width)/2.0f+width,(size-height)/2.0f       );                 PointF pfBL((size-width)/2.0f      ,(size-height)/2.0f+height);                 PointF pfBR((size-width)/2.0f+width,(size-height)/2.0f+height);                 Graphics tgp(&img);                 Bitmap bmp((UINT)size,(UINT)size,&tgp);//Let bmp Resolution equal to img Resolution                 Graphics gp(&bmp);                 gp.SetTransform(&mat);                 gp.DrawImage(&img,pfTL);                 REAL xmin,ymin,xmax,ymax,x,y,rw,rh;                 mat.TransformPoints(&pfTL);                 xmin=xmax=pfTL.X;                 ymin=ymax=pfTL.Y;                 mat.TransformPoints(&pfTR);                 if (xmin>pfTR.X) xmin=pfTR.X;                 if (xmax<pfTR.X) xmax=pfTR.X;                 if (ymin>pfTR.Y) ymin=pfTR.Y;                 if (ymax<pfTR.Y) ymax=pfTR.Y;                 mat.TransformPoints(&pfBL);                 if (xmin>pfBL.X) xmin=pfBL.X;                 if (xmax<pfBL.X) xmax=pfBL.X;                 if (ymin>pfBL.Y) ymin=pfBL.Y;                 if (ymax<pfBL.Y) ymax=pfBL.Y;                 mat.TransformPoints(&pfBR);                 if (xmin>pfBR.X) xmin=pfBR.X;                 if (xmax<pfBR.X) xmax=pfBR.X;                 if (ymin>pfBR.Y) ymin=pfBR.Y;                 if (ymax<pfBR.Y) ymax=pfBR.Y;                 x=xmin;                 y=ymin;                 rw=xmax-x;                 rh=ymax-y;                 Bitmap* clone;                 clone = bmp.Clone(x,y,rw,rh,PixelFormat24bppRGB);//bmp.GetPixelFormat()                 CLSID encoderClsid;                 if (0<=GetEncoderClsid(formats[i],&encoderClsid)) {                     if (Ok==clone->Save(argv[2],&encoderClsid)) {                         wprintf(L"OK to %s  %s  %s  %s\n",argv[0],argv[1],argv[2],argv[3]);                         r=0;                     } else {                         wprintf(L"Error to save %s\n",argv[2]);                         r=4;                     }                 } else {                     wprintf(L"Error to GetEncoderClsid(%s,...)\n",formats[i]);                     r=3;                 }                 delete clone;             } else {                 wprintf(L"Error to get angle %s\n",argv[3]);                 r=2;             }         } else {             wprintf(L"Error to load %s\n",argv[1]);             r=5;         }     }     GdiplusShutdown(gdiplustoken);     return r; }

引用 1 楼 fly_dragon_fly 的回复:fp =fopen(filename,"wb");  fwrite(pngdata,1,pngsize ,fp); fclose(fp) 我一开始就是这样搞的，完全不能看阿


Question: 数字拼接

作为一个C程序员，对  scanf,sscanf,fscanf  printf,sprintf,fprintf 这类函数的用法，还是要做到“拳不离手，曲不离口”的。

引用 7 楼 qq_20242109 的回复:[quote=引用 6 楼 zhangxiangDavaid 的回复:] 0-1是表达式，还是字符串“0-1”? 拼成一个字符串的[/quote] 这样行吗？  int main(void) { 	int arr[] = { 1,2,3,4 }; 	char str[40]; 	sprintf(str, "%d-%d,%d-%d", arr[0], arr[1], arr[2], arr[3]); 	puts(str);   //1-2,3-4 	return 0; }

引用 6 楼 zhangxiangDavaid 的回复:0-1是表达式，还是字符串“0-1”? 拼成一个字符串的

0-1是表达式，还是字符串“0-1”?

引用 3 楼 user-3 的回复:[quote=引用 2 楼 qq_20242109 的回复:] [quote=引用 1 楼 user-3 的回复:] 用 [s[n]]printf 函数 还有其它实现的方法吗，我要把它放到一个数组里[/quote] 什么数组？   {"0-1", "2-3"} 和{0-1, 2-3} 是完全两样的[/quote]  int arr[] = {0,1,2,3} 转换为   引用 4 楼 zhangxiangDavaid 的回复:这样行吗？ printf("%d-%d,%d-%d\n", 0,1,2,3); 哈哈 这个我清楚，如果不使用printf函数,讨论下算法的实现

引用 2 楼 qq_20242109 的回复:[quote=引用 1 楼 user-3 的回复:] 用 [s[n]]printf 函数 还有其它实现的方法吗，我要把它放到一个数组里[/quote] 什么数组？   {"0-1", "2-3"} 和{0-1, 2-3} 是完全两样的

引用 1 楼 user-3 的回复:用 [s[n]]printf 函数 还有其它实现的方法吗，我要把它放到一个数组里

用 [s[n]]printf 函数


Question: 结构体初步，我应该是后面算走过的总路程错了

2个问题  1） scanf("%f %f",&p[i].x,&p[i].y);  要么把xy的定义为float，或者把%f改为%d 2） for(i=1;i<num+1;i++) 应该为i<num， i的值不能取到n

printf里面的%和变量的一一对应关系 scanf里面的%和变量以及变量前加不加&的一一对应关系 是C代码中非常容易出错的地方，而且通常编译还不出错。 所以在编译源代码之前值得专门仔细检查一遍甚至多遍。  “多一少一”问题占程序员常犯错误的10%以上！ 避免“多一少一”问题的方法之一是将比如<10甚至<5的数代入程序片断，搬手指头心算验证一下程序到底应该写为 x、x-1、x+1中的哪个？ <、<=、==、>、>=中的哪个？

把代码写得清晰点，哪怕繁琐一点也不要紧，让自己在debug时更方便 #include <stdio.h> #include <stdlib.h> #include <math.h>  typedef struct tagPoint { 	int x; 	int y; } Point;  typedef struct tagPath { 	Point CurrentPoint; 	struct tagPath * Next; } *Path, PathNode;  double DistanceBetween(const Point p1, const Point p2) { 	const int dx = p1.x - p2.x; 	const int dy = p1.y - p2.y; 	return sqrt(dx * dx + dy * dy); }  void ReadNode(PathNode * node) { 	scanf("%d%d", &node->CurrentPoint.x, &node->CurrentPoint.y); 	node->Next = NULL; }  Path MakePath(int num) { 	PathNode fakehead = {{0, 0}, NULL}; 	Path * ret = &fakehead.Next; 	PathNode * cur = &fakehead; 	while (num --> 0) 	{ 		cur->Next = (PathNode*)malloc(sizeof(PathNode)); 		cur = cur->Next; 		ReadNode(cur); 	} 	return *ret; }  void DeletePath(Path path) { 	while (path) 	{ 		Path next = path->Next; 		free(path); 		path = next; 	} }  double PathLength(const Path path) { 	double result = 0; 	Path p = path; 	while (p->Next) 	{ 		result += DistanceBetween(p->CurrentPoint, p->Next->CurrentPoint); 		p = p->Next; 	} 	return result; }  int main(void) { 	int num = 0; 	scanf("%d", &num); 	Path path = MakePath(num); 	printf("%f", PathLength(path)); 	DeletePath(path); 	return 0; }


Question: 编译原理。求构造C语言的词法分析程序

构造DFA啊..

参考TCC源代码。

分三类即可 1.字符串2.控制字符（包括运算符）3.数值


Question: C 二级指针释放问题

这样的释放并没有问题

这种写法没问题....

不是释放的问题，使用过程中存在越界写操作

仅供参考：//在堆中开辟一个4×5的二维int数组 #include <stdio.h> #include <malloc.h> int **p; int i,j; void main() {     p=(int **)malloc(4*sizeof(int *));     if (NULL==p) return;     for (i=0;i<4;i++) {         p[i]=(int *)malloc(5*sizeof(int));         if (NULL==p[i]) return;     }     for (i=0;i<4;i++) {         for (j=0;j<5;j++) {             p[i][j]=i*5+j;         }     }     for (i=0;i<4;i++) {         for (j=0;j<5;j++) {             printf(" %2d",p[i][j]);         }         printf("\n");     }     for (i=0;i<4;i++) {         free(p[i]);     }     free(p); } //  0  1  2  3  4 //  5  6  7  8  9 // 10 11 12 13 14 // 15 16 17 18 19

越界了吧。。

可能字符串在使用过程中拷贝之后越界了，或者指针的值被修改了。这个代码不会有异常，只是少了一次free而已。


Question: 我采用的是把输入数据转换后放进二维数组，然后用每列和做加法运算，注释写的很清楚，请帮我看看，我debug一天，改了不少错误，但就目前的测试数据是没问题的

由于最多进1 [code=c v3[i+1]+=v3[i]/10; //改为 v3[i+1]+=1;   //更好，更直接 ][/code]

仅供参考：#include <stdio.h> #include <string.h> #define MAXLEN 1000 char a1[MAXLEN]; char a2[MAXLEN]; static int v1[MAXLEN]; static int v2[MAXLEN]; static int v3[MAXLEN]; int i,j,n,L,z; void main(void) {     scanf("%d",&n);     for (j=0;j<n;j++) {         scanf("%s%s",a1,a2);          L=strlen(a1);         for (i=0;i<L;i++) v1[i]=a1[L-1-i]-'0';          L=strlen(a2);         for (i=0;i<L;i++) v2[i]=a2[L-1-i]-'0';          for (i=0;i<MAXLEN;i++) v3[i]=v1[i]+v2[i];          for (i=0;i<MAXLEN;i++) {             if (v3[i]>=10) {                 v3[i+1]+=v3[i]/10;                 v3[i]=v3[i]%10;             }         }          printf("Case %d:\n", j+1);         printf("%s + %s = ", a1, a2);          z=0;         for (i=MAXLEN-1;i>=0;i--) {             if (z==0) {                 if (v3[i]!=0) {                     printf("%d",v3[i]);                     z=1;                 }             } else {                 printf("%d",v3[i]);             }         }         if (z==0) printf("0");          printf("\n");     } } //Sample Input //3 //0 0 //1 2 //112233445566778899 998877665544332211 // //Sample Output //Case 1: //0 + 0 = 0 //Case 2: //1 + 2 = 3 //Case 3: //112233445566778899 + 998877665544332211 = 1111111111111111110

这道题允许 100 001 加起来


Question: c语言中的“*”号

A field width or precision, or both, may be indicated by an asterisk * instead of a digit string.  In this case, an int argument supplies the field width or precision.

* An optional starting asterisk indicates that the data is to be read from the stream but ignored (i.e. it is not stored in the location pointed by an argument).

一般输出是这样： int num=123; printf("%10d\n" ,  num );  //表示按最小数据宽度为10个字符输出整数num 而如果10这里我们想用一个变量来表示，则会采用： int len=10 ; int num=123; printf("%*d\n" , len, num );   输出结果与上面相同。


Question: 指针为什么可以这样使用

指针请看 http://blog.csdn.net/zhangxiangdavaid/article/details/37885275

好像在C语言，一维数组的数组名就是一维指针常量，二维数组名就是二维指针常量。 malloc在C语言里面，就是分配堆空间，返回时堆指针，这里初始化outstr，没有错。

问题: 3) 网友给出的参考代码有个bug . 如果连续重复字符多于9个 .即 count 为两位数以上.... 楼主可以当练习,把它找出来...然后  fix 它....

这是基本的使用方法啊。。

1 指针本来就可以这样用的 2 总有一个地方需要分配，看公司设计需求了 找本基础书翻一下，一般都会讲到


Question: Delaunay三维三角剖分源码

同学，我的毕业设计也是这个，可以给个联系方式，探讨一下吗

引用 9 楼 cmj1109 的回复:你用的是哪种算法啊？是Crust、Power Crust、Cocone？还是生长算法、插入算法、基于四面体的算法等等？ 三维Delaunay生成算法有很多种，比较经典的就是上述几种，你要说明白你用的是哪种算法？而且一般不可能在网上直接有源代码提供。     你好，你对delaunay中的分治法熟悉吗？有些问题想请教你一下？

3DS Max Script或者VBA for AutoCAD里不知道有没有？ 但我知道Matlab和OpenCV里有，输入点云数据，直接调用函数就可以生成三维Delaunay，生成质量挺高的。 Matlab中的相关函数是delaunay和delaunayn，具体的用法在matlab帮助里介绍的挺清楚的，楼主可以看一下。

不知道3DS Max Script或者VBA for AutoCAD里面是不是有内置相关功能？

代码功能归根结底不是别人帮自己看或讲解或注释出来的；而是被自己静下心来花足够长的时间和精力亲自动手单步或设断点或对执行到某步获得的中间结果显示或写到日志文件中一步一步分析出来的。 提醒：再牛×的老师也无法代替学生自己领悟和上厕所！ 单步调试和设断点调试（VS IDE中编译连接通过以后，按F10或F11键单步执行，按Shift+F11退出当前函数；在某行按F9设断点后按F5执行停在该断点处。）是程序员必须掌握的技能之一。

引用 5 楼 acm19931223 的回复:。。。毕不了业了都 出来混，迟早是要还的。

引用 6 楼 zhao4zhong1 的回复:[quote=引用 5 楼 acm19931223 的回复:] 。。。毕不了业了都 出来混，迟早是要还的。[/quote] 搜的论文都是研究生毕业论文，研究生那边都没有人搞，我已经很努力的去做了，只是现在卡在了一些地方，程序有点问题，想找份正确的对比一下，还什么了

。。。毕不了业了都

引用 3 楼 zhao4zhong1 的回复:[quote=引用 2 楼 zhangxiangDavaid 的回复:] 如此搜索 会有效地利用搜索，是现代码农必须掌握的技能之一。[/quote] 说的好

引用 2 楼 zhangxiangDavaid 的回复:如此搜索 会有效地利用搜索，是现代码农必须掌握的技能之一。

如此搜索


Question: 这是本校OJ上的一道题目，本人菜鸟，遂提出来问，求各位大神求指点迷津！（我是想学到更多知识，并不是想要求正确代码，只求大神们指点指点，谢谢）

引用 6 楼 user-1 的回复:你说的对，max也应该改过来才是正解。 不改为什么也不出错呢？我觉得原因是这样的：max不改，那么把2147483648赋值给它的时候，实际上已经超出了long的范围，变成了一个负数。但是，接下来if(px>max)，涉及到一个有符号数和无符号数的比较，需要先把有符号数转换从无符号数，max这个负数就又变回到2147483648了。 http://blog.csdn.net/zdl1016/article/details/2507743  受教了，谢谢

引用 4 楼 user-1 的回复:[quote=引用 2 楼 ma815841356 的回复:] 你好，按你说的把px的类型改成unsigned long后, 输入测试数据1 2 -2147483648 1答案符合题意，但如果输入测试数据为题目的测试用例的话，答案就出错了。  麻烦再看看是否有其他地方的错误，谢谢  顺便请问题目中“32位有符号整数”是什么意思？ 不会吧？我试过了，没错呀。你的输出是什么？ “32位有符号整数”就是4字节的整数，范围是2147483647 ~ -2147483648, 现在一般的编译器的int类型应该就是。 http://blog.csdn.net/xuexiacm/article/details/8122267[/quote]  你好，原先理解错了你的意思，很抱歉，后来我只把px的类型改成unsigned long后，提交后就对了，想请问一下为什么只需要更改px的类型，那max不需要也改成unsigned long吗？本人菜鸟不想只是做对了一道题而已，很希望学到更多知识，谢谢

引用 2 楼 ma815841356 的回复:你好，按你说的把px的类型改成unsigned long后, 输入测试数据1 2 -2147483648 1答案符合题意，但如果输入测试数据为题目的测试用例的话，答案就出错了。  麻烦再看看是否有其他地方的错误，谢谢  顺便请问题目中“32位有符号整数”是什么意思？ 不会吧？我试过了，没错呀。你的输出是什么？ “32位有符号整数”就是4字节的整数，范围是2147483647 ~ -2147483648, 现在一般的编译器的int类型应该就是。 http://blog.csdn.net/xuexiacm/article/details/8122267

你好，刚才理解错了你的意思，很抱歉，后来我只把px的类型改成unsigned long后，提交后就对了，请问为什么只需要更改px的类型，麻烦结合这道题目解释一下，本人菜鸟不想只是做对了一道题而已，很希望学到更多知识，谢谢

楼主的思路和代码都不错，再注意一些细节就行了。 比如，题目已经说了，“就直接给-2147483648分了”，那么试试这个数据： 1 2 -2147483648 1  建议把px的类型改成unsigned long