2013-08-01 182 views
1

我正在嘗試從文件中提取數字。我有限制,我只需要使用open(),read()close()在C中使用regex.h匹配和計算字符串中的任何數字

我已成功讀取數據並保存在緩衝區中。不,我需要將它與RE匹配。 我使用RE =^[0-9] *

這是我這

char buffer[1024] = { NULL }; 
int count = 0; 
int fRead; 

fRead = open("file.in", O_RDONLY); 
read(fRead, buffer, sizeof(buffer)); 
printf("\nFile Opened %s, %lu", buffer, sizeof(buffer)); 

/* Compile regular expression */ 
regex_t re; 
int reti = regcomp(&re, "^[1-9]*", 0); 
if (reti) { 
    fprintf(stderr, "Could not compile regex\n"); 
    exit(1); 
} 

/* Execute regular expression */ 
reti = regexec(&re, buffer, 0, NULL, 0); 
if (!reti) { 
    printf("\nMatch: %d", reti); 
} else if (reti == REG_NOMATCH) { 
    puts("No match"); 
} else { 
    char msgbuf[100]; 
    regerror(reti, &re, msgbuf, sizeof(msgbuf)); 
    fprintf(stderr, "Regex match failed: %s\n", msgbuf); 
    exit(1); 
} 
close(fRead); 

代碼現在的問題是我想算和顯示我在文件中找到的數字。 例如我的文件可能有文字some thing 2 to 3 makes 5,在這種情況下我出去放必須 OUTPUT: 2,3,5 count = 3

回答

3

看一看的man page for regexec。正如您使用的那樣,regexec的返回值是0,表示成功或正面的錯誤代碼。但是,regexec的其他參數是如何獲得有關匹配的更多信息。

爲了方便起見,這裏的regexec的定義:

int regexec(const regex_t *preg, const char *string, size_t nmatch, 
      regmatch_t pmatch[], int eflags); 

的pmatch參數是函數把它的比賽,如果發現他們,nmatch參數告訴pmatch參數有多少元素,因此功能它不會溢出。這與其他語言的「匹配」功能類似,其中pmatch的第一個索引將具有完整的正則表達式匹配,而下列索引將具有子組匹配。這意味着您需要使用子組匹配來從字符串中獲取數字,然後您需要遍歷字符串以查找後續的子組匹配。

首先,實例化regmatch_t堆棧變量來保存結果。這隻需要大小爲2,因此您可以將完整匹配存儲在0索引中,並將子組匹配存儲在1索引中。您還需要更改您的正則表達式,以便它匹配整個字符串,直到達到一個數字。我們會將它傳遞給regexec函數以及nmatch的大小。

每次找到匹配項時,您都需要將字符串的開頭向前移動,以便下次調用regexec時,您將獲得下一個數字而不是相同的。

首先更新正則表達式字符串。

/* if we use .* in the regex it will be greedy and match the last number, not the first. 
    We need to use a + instead of a * for the number so we know there is at least 1. */ 
int reti = regcomp(&re, "[^0-9]*([0-9]+)", REG_EXTENDED); 

然後循環查找所有匹配項。

/* regmatch_t is defined in regex.h */ 
regmatch_t matches[2]; 
int start; 
int end; 

while (1) { 
    reti = regexec(&re, buffer, 2, matches, 0); 

    /* rm_so is the start index of the match */ 
    start = matches[1].rm_so; 
    /* rm_eo is the end index of the match */ 
    end = matches[1].rm_eo; 
    /* break if we didn't find a match */ 
    if (reti) break; 

    /* print the substring that contains the match */ 
    printf("%.*s, ", (end - start), (buffer + start)); 
    /* increment the count of matches */ 
    count = count + 1; 

    /* This is really important! 
    Move the start of the string forward so we don't keep matching the same number! */ 
    buffer = buffer + end; 
} 

/* print the count */ 
printf("count = %d", count); 
+0

我試過這個,但仍然是我的輸出計數爲0;爲什麼這樣? 我已將此代碼複製並粘貼到我的代碼中。 也改變RE,現在RE是[1-9] –

+0

其實它沒有進入While循環由於這個 '匹配[pmatch_index] .rm_so!= -1'條件 –

+0

嗯,測試它我也沒有進入循環。它看起來像regexec標記完全匹配爲0,0(如果你看看匹配[0],你可能會看到rm_so和rm_eo設置爲0)。我會試着弄清楚我在這裏做錯了什麼。 – seanmk