2013-03-24 108 views
1

这是我的代码和问题。代码编译得很好。但是当我运行它。在getMenuOption()中输入菜单选项后,弹出“Segmentation Fault(核心转储)”。哪里不对? 我是一般的编程新手。感谢您提供的帮助。没有指针的分段错误?

#include <stdio.h> 
#include<math.h> 

#define CALCULATE_PI 'a' 
#define CALCULATE_GEOMEAN 'b' 
#define CALCULATE_HARMMEAN 'c' 

void printInstructions (void); 
void printMenuOptions (void); 
int runMenuOption(); 
int getMenuOption(); 
int getLimit(); 
int calculatePi(); 
int calculateGeoMean(); 
int calculateHarmonicMean(); 

int main(void) 
{ 
    printInstructions(); 

    printMenuOptions(); 

    runMenuOption(getMenuOption()); 

    return 0; 

} 

void printInstructions (void) 
{ 
    printf("======================================================\n"); 
    printf("= PI, Geometric Mean, and Harmonic Mean Calculator =\n"); 
    printf("= Please refer to the menu to choose calucaltion =\n"); 
    printf("=Choose desired menu option and press enter to begin =\n"); 
    printf("=  Proceed to follow on-screen instructions  =\n"); 
    printf("======================================================\n\n\n"); 

    return; 
} 

void printMenuOptions (void) 
{ 
    printf("3 choices: Please enter a VALID letter.\n"); 
    printf("Choice 'a' = Calcualtes PI\n"); 
    printf("Choice 'b' = Calculates Geometric Mean\n"); 
    printf("Choice 'c' = Calculates Harmonic Mean\n\n"); 

    return; 
} 

int runMenuOption (int getMenuOption()) 
{ 
    char option; 
    double answer, 
      Pi = 0.0, 
      geoMean = 0.0; 

    option = getMenuOption(); 

    switch (option) 
    { 
     case CALCULATE_PI: 
      calculatePi(getLimit()); 
      answer = Pi; 
      break; 
     case CALCULATE_GEOMEAN: 
      calculateGeoMean(getLimit()); 
      answer = geoMean; 
     case CALCULATE_HARMMEAN: 
      printf("Harmonic Mean"); 
      break; 
     default: 
      printf("Incorrect Character!\n"); 
      printf("Try again"); 
      break; 
    } 

    printf("Your answer is %5p", &answer); 

    return 0; 
} 

int getMenuOption (void) 
{ 
    char option; 

    printf("Please enter choice: "); 

    scanf("%c", &option); 

    return option; 
} 

int getLimit() 
{ 
    int limit; 

    scanf("%d", &limit); 

    return limit; 
} 

int calculatePi (void) 
{ 
    int limit, 
    count = 0, 
    Pi = 0; 

    printf("Please enter the PI limit: "); 

    limit = getLimit(); 

    for (count = 1; count <= limit; count++) 
    { 
     Pi += 1/count; 
    } 

    return sqrt(Pi * 6); 
} 

int calculateGeoMean() 
{ 
    int limit, 
     userValue = 0, 
     count = 0; 
    double geoMean = 0; 

    limit = getLimit(); 

    while(count <= limit) 
    { 
     if (userValue <= 0) 
      printf("Incorrect. Try again"); 
     else 
     { 
      count++; 
      userValue *= userValue; 
     } 

    } 
    geoMean = userValue; 

    return sqrt(userValue); 
} 

int calculateHarmonicMean() 
{ 
    int limit, 
     userValue = 0, 
     count = 0; 
    double harmMean = 0; 

    limit = getLimit(); 

    while(count <= limit) 
    { 
     if (userValue <= 0) 
      printf("Incorrect. Try again"); 
     else 
     { 
      count++; 
      userValue *= 1/userValue; 
     } 

    } 
    harmMean = userValue; 

    return limit/userValue; 
} 

回答

6

这个函数定义是完全错误的。

int runMenuOption (int getMenuOption()) 

要么你可以传递的getMenuOption返回值这样

int runMenuOption (int option) 

你不应该任意值传递给该函数并调用getMenuOptionrunMenuOption。你正在做这两个,这是不正确的。

+0

@ComInfoSystems - 你的问题解决吗? – neham 2013-03-24 02:25:43

2
int runMenuOption (int getMenuOption()) 

这是你的问题。

这应该是:

int runMenuOption (int opt) 

而且,你不应该叫内runMenuOptiongetMenuOption()因为你打电话getMenuOption(),你把它传递给runMenuOption作为参数。 runMenuOption应该只有一个switch声明。

0

您需要修改功能的定义,从int runMenuOption (int getMenuOption())int runMenuOption (int option)。在调用中,将调用getMenuOption()并将输出放入被调用函数的stack frame中。

0

根据您的runMenuOption函数的声明,它需要一个指向它返回一个整数作为其第一个参数的函数:

int runMenuOption (int getMenuOption()) 

然后调用该函数在这一行:

option = getMenuOption(); 

这很好。然而,问题就出在这行:

runMenuOption(getMenuOption()); 

在这里,您呼叫的getMenuOption函数并传递返回值到runMenuOption功能。但是,你应该做的是传递函数本身作为参数:

runMenuOption(getMenuOption); 

你得到一个分段错误的原因是因为从getMenuOption函数的返回值被视为一个函数指针,你的程序正试图在该地址调用一个函数,这当然是无效的。

+0

@Armin:我刚刚测试了我的解决方案,它在GCC v4.5.3上正常工作。在做:runMenuOption(&getMenuOption)也将工作,但绝对不会运行MenuOption(getMenuOption())。你能否详细说明为什么你认为这是错误的?编辑:另请注意,通过:“runMenuOption(getMenuOption());”我指的是他在main函数中调用runMenuOption的行,而不是runMenuOption函数原型。 – Isuru 2013-03-24 02:13:20

+0

我脑子里有不同的东西,你的建议虽然不寻常,但它的作用。除非你编辑,否则我不能再取消选举。 – 2013-03-24 02:17:35

+0

我只是想通知作者分段错误的确切原因。该解决方案还具有对作者的原始程序进行微小更改的优点。 – Isuru 2013-03-24 02:21:41