2014-02-11 62 views
0

我正在處理一個包含文本的char [],它應該表示一個雙精度數值或一個長數字。
我需要編寫一個函數來檢測上面哪些數據類型被表示(如果有的話)。檢測一個字符串是一個雙精度還是長精度C

我想過使用strtol()並檢查它是否無法解析整個字符串,如果失敗,請使用strtod()。

我很高興看到是否有更好的選擇這樣做。 謝謝。

+4

['strtol'](http://en.cppreference.com/w/c/string/byte/strtol)和['strtod'](http://en.cppreference.com/w/c/string/byte/strtof)函數幾乎是這裏的答案。 –

回答

2

我想過使用strtol()並檢查它是否無法解析整個字符串,如果失敗,請使用strtod()。

我認爲這是一個好主意,我不認爲有更好的主意。實現你自己的解析例程通常是一個壞主意。

在調用strtol以避免錯誤的否定之前,我會從尾部的空白處修剪字符串。

+0

'strtol()'不關心尾隨空白;它將它作爲字符串的未解釋部分的一部分。 –

+0

@JonathanLeffler如果有空白,str​​tol不會解析整個字符串,它會停在第一個空白處,從而「失敗」解析整個字符串,因此是否定的。 –

-2
You can use the following code to detect that. 

char* isDouble = strchr(string, '.'); 
if (isDouble) { 
    // is Double here 
}else { 
    // is long here 
} 
+0

問題在於它依賴於區域,所以你不能假設浮動總是有「。」它也可能是一個「,」。 –

+0

'1E-6'怎麼樣?沒有小數點,但它代表雙倍。 –

1

strtol() and strtod()是正確的做法。一定要使用errno來檢測整數溢出。 2獨立的功能如下:

int Is_long(const char *src, long *dest) { 
    char *endptr; 
    // Clear, so it may be tested after strtol(). 
    errno = 0; 
    // Using 0 here allows 0x1234, octaland decimal 1234. 
    long num = strtol(src, &endptr, 0); 
    // If +/- overflow, "" or has trailing text ... 
    if (errno || endptr == src || *endptr != '\0') { 
    return 0; 
    } 
    if (dest) *dest = num; 
    return 1; 
} 

int Is_double(const char *src, double *dest) { 
    char *endptr; 
    // In this case, detecting over/undeflow IMO is not a concern, so ignore it. 
    double num = strtod(src, &endptr); 
    // If "" or has trailing text ... 
    if (endptr == src || *endptr != '\0') { 
    return 0; 
    } 
    if (dest) *dest = num; 
    return 1; 
} 

@KlasLindbäck確實帶來了的怎麼辦尾部空白的好點。這個答案假定它是無效的。