我做了一些研究,以尋找sscanf()
的源代碼。但我找不到我的問題的答案。sscanf()是否支持「遞歸」緩衝區?
,當我們以這種方式使用sscanf()
:
char str[50] = "5,10,15";
int x;
sscanf(str,"%d,%s",&x,str);
是否sscanf的()支持 「遞歸」 緩衝str
?
我做了一些研究,以尋找sscanf()
的源代碼。但我找不到我的問題的答案。sscanf()是否支持「遞歸」緩衝區?
,當我們以這種方式使用sscanf()
:
char str[50] = "5,10,15";
int x;
sscanf(str,"%d,%s",&x,str);
是否sscanf的()支持 「遞歸」 緩衝str
?
它不會從自我修改緩衝區中斷。但爲了使它(尾)遞歸,你必須讀到字符串的末尾。
的代碼片段:
char str[]="5,10,15";
int a[10]={0},x = 0;
while (sscanf(str,"%d,%s",a+ x++,str)>1);
讀取所有的整數。
由於這不是真正的遞歸,並且要讀取的字符串不會覆蓋字符串中的asciiz,所以我認爲這是「安全」的含義:只能在家中試用。
巧妙的把戲。顯然效率低於使用%n和循環增加到str的偏移量,這可能是問題的要求,但這是一個好主意。我覺得,你必須以相當愚蠢的方式實施sscanf,因爲這不起作用。 –
一般我會建議這個。如果它的作用不是這個意思,那它會在所有的角落案例中。要確定的是,你必須檢查你正在使用的實現的源代碼。如果你希望它是可移植的,那就馬上忘記它,除非你將它看作是一種保證行爲的libc規範。使用strchr()
來查找下一個分隔符並更新字符串指針以指向下一個字符。
scanf家族函數讀取格式說明符並逐個進行轉換。在您的示例代碼中:
char str[50] = "5,10,15";
int x;
sscanf(str,"%d,%s",&x,str);
它可能工作,因爲它讀取整數第一個和另一個c字符串。這裏沒有問題,因爲原始str
被新值覆蓋。
但考慮以下幾點:
char str[50] = "5 10 15";
int x;
sscanf(str,"%s %d",str, &x);
它首先從原始值讀取5
並覆蓋str
,並作爲str
年底已因達到隨後的格式說明%d
將一無所有從str
閱讀終止前%s
閱讀。
這只是一個反例,表明這是一個壞主意,並且不起作用。所以你可以說這會在某個時候調用未定義的行爲或者導致其他問題。
同意。即使正確使用,遞歸sscanf()也可能會觸發下一位維護代碼的程序員的所有警報,從而使其重複這種不重要的演繹。尊重你的同事們的時間。保持你的代碼可讀,不要讓他們想! – deStrangis
採用strtok()
解決的幾乎相同的問題,我,即,使用sscanf()
遞歸提取char*
的內容(通過的空間的雙重的分離的列表中,例如"1.00 2.01 ..."
)成一個雙陣列(例如array[1]=1.00
,array[2]=2.01
,...)。
下可能會有所幫助,如果我相信我理解你的問題:
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
int main(int argc, char** argv)
{
char str[]= "5,10,15";
char* token;
int x[3];
token = strtok(str, ",");
for(int i=0; i<3; i++){
sscanf(token, "%d", &x[i]);
token = strtok(NULL, ",");
}
for(int i=0; i<3; i++) printf("%d\n", x[i]);
return 0;
}
在運行時,它產生:
5
10
15
爲strtok()
一個有用的說明,請參見http://www.cplusplus.com/reference/cstring/strtok/。
從同一時間讀取和寫入同一個內存區通常不是一個好主意。 –
我知道這一點。但它可以由sscanf函數支持。爲什麼我在尋找。可能是scanf沒有問題。這將允許我優化我的代碼。我將不必添加另一個緩衝區並複製... – MOHAMED
+1不同的問題 –