2015-09-04 41 views
2

當運行使用Xcode的這個小C腳本,我得到這個消息:浮動看作是一個雙

Format specifies type 'float *' but the argument has type 'double" at scanf("%f", v) and scanf("%f", i).

我不明白這一點,因爲我還沒有宣佈任何double類型變量。

int main(int argc, const char * argv[]) { 
    char choice[10]; 

    float v; 
    float i; 
    float r; 

    printf("What would you like to calculate?: "); 
    scanf("%s", choice); 
    printf("\nYou chose: \n""%s", choice); 

    if (strcmp(choice, "r") == 0) 
    { 
     printf("\nPlease enter voltage (V): \n"); 
     scanf("%f", v); 

     printf("\nPlease enter current (I): \n"); 
     scanf("%f", i); 

     r = v/i; 

     printf("%f", r); 
    } 
} 

任何想法?

回答

5

你得到警告,因爲你沒有一個指針傳遞給一個浮動(float*)到函數scanf。編譯器告訴你它是雙重的,因爲scanfvariadic function。變量參數受默認參數提升的影響,其中某些數據類型的參數被轉換爲更大的數據類型。在這種情況下,float被提升爲double

在C函數修改變量vi的唯一途徑,而choice是通過他們爲指針,所以你需要指針傳遞給scanf,使用運營商&「的地址」。

您的代碼應該是這樣的:

int main(int argc, const char * argv[]) { 
    char choice[10]; 

    float v; 
    float i; 
    float r; 

    printf("What would you like to calculate?: "); 
    scanf("%9s", &choice); /* this specifier prevents overruns */ 
    printf("\nYou chose: \n""%s", choice); 

    if (strcmp(choice, "r") == 0) 
    { 
     printf("\nPlease enter voltage (V): \n"); 
     scanf("%f", &v); /* use a pointer to the original memory */ 

     printf("\nPlease enter current (I): \n"); 
     scanf("%f", &i); /* use a pointer to the original memory */ 

     r = v/i; 

     printf("%f", r); 
    } 
} 

還請注意,我用的格式說明%9s。這樣,如果用戶輸入9個以上的字符,相鄰的內存不會被覆蓋。您必須爲空字符\0保留數組的最後一個元素,因爲C中的字符串以\0結尾。

2

您必須使用&操作。例如用scanf("%f", &v);代替scanf("%f", v);。這會將變量的地址(而不是值)傳遞給scanf()

2

你必須寫scanf("%f", &i);等,只要你想的變量作爲指針傳遞爲C沒有引用類型,如C++

4

我不明白這一點,因爲我沒有任何聲明double類型變量。

如果沒有可見的原型來指示函數對給定參數期望的類型,或者當該參數在一組可變參數中時,則對該參數執行默認參數提升。這提供了與ANSI C代碼之前的兼容性,假設這些促銷是在全部參數上執行的。

在這種情況下,scanf()是可變參數,這個原型:

int scanf(const char *fmt, ...); 

所以的一切,但格式會默認參數推廣。對於float類型的參數,這是一個推廣double,而這也正是你double來源。

當然,正如其他答案所描述的,你根本不應該通過float,而是一個指向它的指針。