![](/img/trans.png)
[英]Standard C function atof returns segmentation faults when using with strtok
[英]Using atof() function in C with multiple input values
該程序的目標是創建一個函數,該函數讀取單個字符串,用戶鍵入的命令(最終是與機器人結合使用的程序),該函數由未知的命令字(存儲並打印為命令)組成,並且未知數量的十進制參數(數量存儲並打印為num,參數將作為浮點值存儲在數組參數中)。 在用戶輸入中,命令和參數將用空格分隔。 我相信我要從字符串中提取十進制值時出現的問題是atof函數。 我究竟做錯了什么? 感謝您的幫助!
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void func(char *input, char *command, int *num, float *params);
int main()
{
char input[40]={};
char command[40]={};
int num;
float params[10];
printf("Please enter your command: ");
gets(input);
func(input,command,&num,params);
printf("\n\nInput: %s",input);
printf("\nCommand: %s",command);
printf("\n# of parameters: %d",num);
printf("\nParameters: %f\n\n",params);
return 0;
}
void func(char *input, char *command, int *num, float *params)
{
int i=0, k=0, j=0, l=0;
int n=0;
while(input[i]!=32)
{
command[i]=input[i];
i++;
}
for (k=0; k<40;k++)
{
if ((input[k]==32)&&(input[k-1]!=32))
{
n++;
}
}
*num=n;
while (j<n)
{
for (l=0;l<40;l++)
{
if((input[l-1]==32)&&(input[l]!=32))
{
params[j]=atof(input[l]);
j++;
}
}
}
}
示例輸出屏幕:
Please enter your command: Move 10 -10
Input: Move 10 -10
Command: Move
# of parameters: 2
Parameters: 0.000000
理想情況下,Parameters輸出的輸出應為“ 10 -10”。 謝謝!
將atof(input[l])
更改為atof(input + l)
。 input[l]
是單字符,但您想從l
位置獲取子字符串。 另請參見strtod()
函數。
其他人已經在您的代碼中提到了該問題,但是我是否建議您看看strtod()
呢?
盡管atof()
和 strtod()
為您strtod()
空格(因此您無需手動執行此操作),但strtod()
會將您指向數字的末尾,以便您知道從何處繼續:
while(j < MAX_PARAMS) // avoid a buffer overflow via this check
{
params[j] = strtod(ptr, &end); // `end` is where your number ends
if(ptr == end) // if end == ptr, input wasn't a number (say, if there are none left)
break;
// input was a number, so ...
ptr = end; // continue at end for next iteration
j++; // increment number of params
}
請注意,上述解決方案無法區分無效參數(例如, foo
而不是3.5
)和缺失參數(因為我們已經敲了最后一個參數)。 您可以通過執行以下操作進行檢查: if(!str[strspn(str, " \\t\\v\\r\\n\\f")])
---這將檢查我們是否在字符串的末尾(但允許尾隨空白)。 請參閱第二個旁注以了解其功能。
旁注:
您可以使用' '
而不是32
來檢查空間; 這有兩個優點:
供以后參考,此技巧可以幫助您跳過空格: ptr += strspn(ptr, " \\t\\v\\r\\n\\f");
。 strspn
返回字符串開頭與集合相匹配的字符數(在本例中為" \\t\\v\\r\\n"
)。 查看文檔以獲取更多信息。
strspn
示例: strspn("abbcbaa", "ab");
返回3
因為您在c
(不匹配)之前有aab
(匹配)。
您正在嘗試將char
轉換為float
,
params[j]=atof(input[l]);
您應該獲取浮點數的整個單詞(子字符串)。
例如, "12.01"
以5個字符結尾的空終止字符串,並將其傳遞給atof
, atof("12.01")
,它將返回12.01
的double
。
因此,您應該首先為每個float參數提取字符串並將其傳遞給atof
避免將字符與ascii值進行比較,而是可以直接使用' '
(空格)。
可以使用strlen()
或strnlen()
來查找輸入字符串的長度,而不是使用具有固定大小的for循環。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.