[英]How do I remove my segmentation faults in my C program?
I am trying to program a calculator that converts a an infix expression to a postfix expression and then evaluates the postfix expression.我正在尝试编写一个计算器,将中缀表达式转换为后缀表达式,然后计算后缀表达式。 I have included my code here for your reference.
我在这里包含了我的代码供您参考。
My postfix code works perfectly fine as I have tested it on its own.我的 postfix 代码运行良好,因为我已经对其进行了单独测试。 But when I use the postfix code in my infix file for evaluation purposes, I get segmentation faults.
但是当我在中缀文件中使用后缀代码进行评估时,我会遇到分段错误。
I have tried using gdb to debug my segfaults and it points me towards my is_operand() function in my postfix file.我曾尝试使用 gdb 调试我的段错误,它指向我的后缀文件中的 is_operand() 函数。 I backtraced to see how it got to that function, and I noticed that when my infix program calls the postfix_evaluate function, it calls this is_operand() function which gives me this error.
我回溯以查看它是如何到达该函数的,并且我注意到当我的中缀程序调用 postfix_evaluate 函数时,它调用了这个 is_operand() 函数,这给了我这个错误。 I have no idea how to fix this issue as I'm relatively new to C coding.
我不知道如何解决这个问题,因为我对 C 编码比较陌生。 Would appreciate some help!
希望得到一些帮助!
My infix.c file:我的 infix.c 文件:
#include "infix.h"
// evaluate expression stored as an array of string tokens
double evaluate_infix_expression(char ** args, int nargs) {
// Write your code here
char ** postfix = malloc(sizeof(char*) * nargs);
postfix = inftopost(args, nargs);
int count=0;
for(int i=0;i<nargs;i++){
if(is_openbracket(*(args+i))){
count++;
}
}
int infix_size = nargs - count;
double final = evaluate_postfix_expression(postfix, infix_size);
return final;
}
//--------------------------------------------------------
char ** inftopost(char** args, int nargs){
char ** postfix = malloc(sizeof(char*) * nargs);
struct double_stack* infix = double_stack_new(nargs);
int counter=0;
for(int i=0;i<nargs;i++){
if(is_operand(args[i])){
postfix[counter]=args[i];
counter++;
}
else if(is_openbracket(args[i])){
double_stack_push(infix,'(');
}
else if(is_operator(args[i])){
while(op_precedence(infix, *args[i], infix)){
char flag3 = double_stack_pop(infix);
postfix[counter]= flag3;
counter++;
}
double_stack_push(infix, *args[i]);
}
else if(is_closedbracket(args[i])){
int flag;
while(!is_openbracket_stack(infix, args)){
char flag = double_stack_pop(infix);
postfix[counter] =flag;
counter++;
}
double_stack_pop(infix);
}
}
int top = infix->items[infix->top-1];
int flag2;
while(is_operator(args[top])){
int top = infix->items[infix->top-1];
char flag2 = double_stack_pop(infix);
postfix[counter] = flag2;
counter++;
}
return postfix;
}
bool is_openbracket(char * token){
if(token[0] == '('){
return true;
}
return false;
}
bool is_closedbracket(char * token){
if( token[0] == ')'){
return true;
}
return false;
}
bool is_openbracket_stack(struct double_stack * input, char ** infix){
int top = input->items[input->top-1];
if(infix[top][0] == '('){
return true;
}
return false;
}
bool op_precedence(struct double_stack * input, char**infix, char * token){
int top = input->items[input->top-1];
int top_stack_precedence =0;
if(infix[top][0] == '^'){
top_stack_precedence = 4;
}else if((infix[top][0] == '*') || (infix[top][0] == '/')){
top_stack_precedence = 3;
}else if((infix[top][0] == '+') || (infix[top][0] == '-')){
top_stack_precedence = 2;
}
int token_precedence =0;
if(token[0] == '^'){
token_precedence = 4;
}else if((token[0] == '*') || (token[0] == '/')){
token_precedence = 3;
}else if((token[0] == '+') || (token[0] == '-')){
token_precedence = 2;
}
if(token_precedence>=top_stack_precedence){
return true;
}
return false;
}
My postfix.c file:我的 postfix.c 文件:
#include "postfix.h"
bool is_operator(char * token){
if(token[0] == '+' || token[0]=='-' || token[0]== 'X' || token[0] == '/' || token[0] == '^'){
return true;
}
return false;
}
bool is_operand(char*token){
if(token[0]>='0' && token[0]<='9'){
return true;
}else if((token[0]=='-' || token[0]=='.') && (*(token+1)<='9' && *(token+1)>='0')){
return true;
}
return false;
}
// evaluate expression stored as an array of string tokens
double evaluate_postfix_expression(char ** args, int nargs) {
// Write your code here
struct double_stack *stack = double_stack_new(nargs);
for(int i=0;i<nargs;i++){
if(is_operand(*(args+i))){
double_stack_push(stack,atof(*(args+i)));
}
else if( is_operator(args[i])) {
double token, op1, op2;
op2 = double_stack_pop(stack);
op1 = double_stack_pop(stack);
char operator_check = args[i][0];
switch (operator_check){
case '+':
token = op2+op1;
double_stack_push(stack,token);
break;
case '-':
token = op1-op2;
double_stack_push(stack,token);
break;
case 'X':
token = op1*op2;
double_stack_push(stack,token);
break;
case '/':
token= op1/op2;
double_stack_push(stack,token);
break;
case '^':
token= pow(op1,op2);
double_stack_push(stack,token);
break;
default: break;
}
}
}
return double_stack_pop(stack);
}
I havent included my .h files here, but I do have all necessary headerfiles and other necessary stuff.我没有在这里包含我的 .h 文件,但我有所有必要的头文件和其他必要的东西。
malloc(nargs * sizeof(char *))
allocates space for an array of pointers, it does not allocate space for any of those pointers. malloc(nargs * sizeof(char *))
为指针数组分配空间,它不会为任何这些指针分配空间。 You need to do something like postfix[i] = malloc(... * sizeof(char))
for every element of your array before trying to index into any of those strings.postfix[i] = malloc(... * sizeof(char))
操作。postfix
to the result of malloc
, you should not reassign it (you do this on the line postfix = inftopost(args, nargs)
).postfix
分配给malloc
的结果后,您不应重新分配它(您在postfix = inftopost(args, nargs)
行上执行此操作)。 Otherwise, you are simply 'throwing away' the result of your malloc. As a general point of guidance, you should try to only use malloc
and free
within initialization functions.作为一般指导,您应该尝试仅在初始化函数中使用
malloc
和free
。 For example, you could write the functions create_stack
and destroy_stack
.例如,您可以编写函数
create_stack
和destroy_stack
。 All other stack methods then take a stack as a first argument, and perform some operation on that stack (popping, pushing, etc.).所有其他堆栈方法然后将堆栈作为第一个参数,并在该堆栈上执行一些操作(弹出、推送等)。
If you would like more elaboration on program design in C please leave a comment.如果您想更详细地了解 C 中的程序设计,请发表评论。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.