[英]Parsing Large File in C
對於一個類,我已經被賦予了使用pthreads,openmp和MPI並行編寫基數排序的任務。 在這種情況下我選擇的語言是C - 我不太了解C ++。
無論如何,我正在閱讀文本文件的方式導致大約500MB文件大小的分段錯誤。 這些文件是行分隔的32位數字:
12351
1235234
12
53421
1234
我知道C,但我不太清楚; 我使用我所知道的東西,在這種情況下,我所知道的事情非常低效。 我閱讀文本文件的代碼如下:
#include <stdlib.h>
#include <stdio.h>
#include <stdint.h>
#include <string.h>
#include <math.h>
int main(int argc, char **argv){
if(argc != 4) {
printf("rs_pthreads requires three arguments to run\n");
return -1;
}
char *fileName=argv[1];
uint32_t radixBits=atoi(argv[2]);
uint32_t numThreads=atoi(argv[3]);
if(radixBits > 32){
printf("radixBitx cannot be greater than 32\n");
return -1;
}
FILE *fileForReading = fopen( fileName, "r" );
if(fileForReading == NULL){
perror("Failed to open the file\n");
return -1;
}
char* charBuff = malloc(1024);
if(charBuff == NULL){
perror("Error with malloc for charBuff");
return -1;
}
uint32_t numNumbers = 0;
while(fgetc(fileForReading) != EOF){
numNumbers++;
fgets(charBuff, 1024, fileForReading);
}
uint32_t numbersToSort[numNumbers];
rewind(fileForReading);
int location;
for(location = 0; location < numNumbers; location++){
fgets(charBuff, 1024, fileForReading);
numbersToSort[location] = atoi(charBuff);
}
在一個5000萬個數字(約500MB)的文件中,我在所有地方的倒帶時遇到了分段錯誤。 我對文件流如何工作的了解幾乎不存在。 我的猜測是它試圖沒有足夠的內存或其他東西,但我不知道。
所以,我在這里有一個兩個部分:如何重繞分段錯誤? 我只是在倒帶前做一份糟糕的工作,而不是檢查一些系統調用我應該這樣做嗎?
而且,從文本文件中讀取任意數量的數字的更有效方法是什么?
任何幫助表示贊賞。
我認為這里最可能的原因是(具有諷刺意味的是) 堆棧溢出 。 您的numbersToSort
數組在堆棧上分配,並且堆棧具有固定大小(因編譯器和操作系統而異,但1 MB是典型數字)。 您應該使用malloc()
在堆上(具有更多可用空間)動態分配numbersToSort
:
uint32_t *numbersToSort = malloc(sizeof(uint32_t) * numNumbers);
不要忘記以后解除分配:
free(numbersToSort);
我還要指出,如果有任何空白行,那么用於計算行數的首通循環將失敗。 這是因為在空行上,第一個字符是'\\n'
, fgetc()
將使用它; 下一次調用fgets()
將會讀取以下行,並且您將跳過計數中的空白行。
問題出在這一行
uint32_t numbersToSort[numNumbers];
您正在嘗試在堆棧中分配一個巨大的數組,您的堆棧大小為幾KB(此外,較舊的C標准不允許這樣)。 所以你可以試試這個
uint32_t *numbersToSort; /* Declare it with other declarations */
/* Remove uint32_t numbersToSort[numNumbers]; */
/* Add the code below */
numbersToSort = malloc(sizeof(uint32_t) * numNumbers);
if (!numbersToSort) {
/* No memory; do cleanup and bail out */
return 1;
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.