C语言代码编译警告修复后运行异常,求解决方案
C语言代码警告修复后运行异常问题求助
我写了一段C语言代码,编译时出现5条警告,分为两类:‘将赋值结果作为条件未加括号’和‘非void函数未返回值’。原代码带警告时能正常运行且输出正确,但按照编译器提示修改后程序反而无法正常运行。附上代码和警告信息,求帮忙理解并解决问题:
原代码
#include <stdio.h> #include <stdlib.h> char s1(char *random); char s2(char *s2_input, int index); char strfilter(char *random, char *s2_input, char replacement); int main() { int s1_index = 41; char s1_random[s1_index]; s1(s1_random); printf("\ns1 = "); puts(s1_random); printf("s2 = "); int s2_index = 21; char s2_input[s2_index]; s2(s2_input, s2_index); if(s2_input[1] == '\0') { printf("size too small"); exit(0); } printf("ch = "); char replacement = getchar(); printf("\n"); int filter_index = 41; strfilter(s1_random, s2_input, replacement); printf("\ns1 filtered = "); puts(s1_random); } char s1(char *random) { int limit = 0; char characters; while(characters = ('A' + (rand() % 26))) /* random generatro */ { if(limit == 41) { *(random + 41 - 1) = '\0'; break; } *(random + limit) = characters; limit++; } } char s2(char *s2_input, int index) { char array[21] = "123456789012345678901"; /* populated array to make sure no random memory is made */ char input; int count = 0; int check = 0; while(input = getchar() ) { if(input == '\n') { *(s2_input + count) = '\0'; break; } else if(input < 65 || input > 90) { printf("invalid input"); exit(0); } *(s2_input + count) = input; count++; } index = count; } char strfilter(char *random, char *s2_input, char replacement) /* replacement function */ { while(*s2_input) { char *temp = random; while(*temp) { if(*temp == *s2_input) *temp = replacement; temp++; } s2_input++; } }
编译警告信息(中文翻译)
matthew.c:41:22: 警告:将赋值结果作为条件使用却未加括号 [-Wparentheses] while(characters = ('A' + (rand() % 26))) /* random generatro */ ~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~ matthew.c:41:22: 提示:给赋值语句加上括号可消除此警告 while(characters = ('A' + (rand() % 26))) /* random generatro */ ^ ( ) matthew.c:41:22: 提示:使用'=='将赋值转换为相等比较 while(characters = ('A' + (rand() % 26))) /* random generatro */ ^ == matthew.c:51:1: 警告:非void函数未返回值 [-Wreturn-type] } ^ matthew.c:61:17: 警告:将赋值结果作为条件使用却未加括号 [-Wparentheses] while(input = getchar() ) ~~~~~~^~~~~~~~~~~ matthew.c:61:17: 提示:给赋值语句加上括号可消除此警告 while(input = getchar() ) ^ ( ) matthew.c:61:17: 提示:使用'=='将赋值转换为相等比较 while(input = getchar() ) ^ == matthew.c:80:1: 警告:非void函数并非所有控制路径都有返回值 [-Wreturn-type] } ^ matthew.c:96:1: 警告:非void函数未返回值 [-Wreturn-type] } ^ 生成了5条警告。
问题分析与修复方案
1. 关于“将赋值结果作为条件未加括号”的警告
你程序修改后崩溃的核心原因是错误地把赋值=改成了相等判断==,而不是按提示给赋值加括号:
- 原代码中
while(characters = ('A' + (rand()%26)))是故意把赋值结果作为循环条件:因为生成的字符是大写字母(ASCII 65-90),永远非0,循环会一直执行直到limit达到41后break。如果改成==,条件几乎永远为假,循环直接跳过,s1_random没被初始化,后续操作必然出错。 - 同样,
s2函数里的while(input = getchar())也不能改成==,否则循环不会读取输入,s2_input为空,直接触发size too small退出程序。 - 正确修复方式:给赋值语句加括号,明确告知编译器这是故意的写法:
// s1函数里的循环改成 while( (characters = ('A' + (rand() % 26))) ) // s2函数里的循环改成 while( (input = getchar()) )
2. 关于“非void函数未返回值”的警告
你的s1、s2、strfilter三个函数声明返回char,但实际没有任何返回语句,这属于C语言的未定义行为(虽然有时能运行,但存在风险):
- 这三个函数都是通过指针参数修改外部变量,完全不需要返回值。正确修复方式:把它们的返回类型改成
void,同时更新函数声明和定义:// 声明改成 void s1(char *random); void s2(char *s2_input, int index); void strfilter(char *random, char *s2_input, char replacement); // 定义改成 void s1(char *random) { ... } void s2(char *s2_input, int index) { ... } void strfilter(char *random, char *s2_input, char replacement) { ... }
修复后的完整代码
#include <stdio.h> #include <stdlib.h> void s1(char *random); void s2(char *s2_input, int index); void strfilter(char *random, char *s2_input, char replacement); int main() { int s1_index = 41; char s1_random[s1_index]; s1(s1_random); printf("\ns1 = "); puts(s1_random); printf("s2 = "); int s2_index = 21; char s2_input[s2_index]; s2(s2_input, s2_index); if(s2_input[1] == '\0') { printf("size too small"); exit(0); } printf("ch = "); char replacement = getchar(); printf("\n"); strfilter(s1_random, s2_input, replacement); printf("\ns1 filtered = "); puts(s1_random); } void s1(char *random) { int limit = 0; char characters; while( (characters = ('A' + (rand() % 26))) ) { if(limit == 41) { *(random + 40) = '\0'; break; } *(random + limit) = characters; limit++; } } void s2(char *s2_input, int index) { char input; int count = 0; while( (input = getchar()) ) { if(input == '\n') { *(s2_input + count) = '\0'; break; } else if(input < 'A' || input > 'Z') // 用字符常量更易读 { printf("invalid input"); exit(0); } *(s2_input + count) = input; count++; } } void strfilter(char *random, char *s2_input, char replacement) { while(*s2_input) { char *temp = random; while(*temp) { if(*temp == *s2_input) *temp = replacement; temp++; } s2_input++; } }
额外优化:把input < 65 || input >90改成input < 'A' || input > 'Z',代码可读性更强;把*(random +41-1)简化成*(random+40),逻辑更清晰。
内容的提问来源于stack exchange,提问作者user20544996
相关产品推荐
相关产品推荐

