【问题标题】:Word counting program using multi threading: Large file size使用多线程的字数统计程序:大文件大小
【发布时间】:2014-02-16 18:40:30
【问题描述】:

我正在尝试编写一个程序来计算大文件中的单词。我正在做多线程。但是我的程序给出了分段错误,我只是被困在这里。我正在寻找导师的任何建议:代码如下:

输入:file name 输出:分段错误

代码为:

   #include <stdio.h>
#include <pthread.h>
#include <stdlib.h>


struct thread_data{
    FILE *fp;
    long int offset;
    int start;
    int blockSize;
};

int words=0;  

void *countFrequency(void* data){

    struct thread_data* td=data;
    char *buffer = malloc(td->blockSize);

    int i,c;
    i=0;c=0;
    enum states { WHITESPACE, WORD };
    int state = WHITESPACE;

    fseek(td->fp, td->offset, td->start);

        char last = ' '; 
        while ((fread(buffer, td->blockSize, 1, td->fp))==1){

            if ( buffer[0]== ' ' || buffer[0] == '\t'  ){
            state = WHITESPACE;
            }
            else if (buffer[0]=='\n'){
            //newLine++;
                state = WHITESPACE;
            }
            else {
                if ( state == WHITESPACE ){
                    words++;
                }
                state = WORD;
            }
            last = buffer[0];
    }
    free(buffer);

    pthread_exit(NULL);

    return NULL;
}

int main(int argc, char **argv){

    int nthreads, x, id, blockSize,len;
    //void *state;
    FILE *fp;
    pthread_t *threads;

    struct thread_data data[nthreads];

    if (argc < 2){
        fprintf(stderr, "Usage: ./a.out <file_path>");
        exit(-1);
    }

    if((fp=fopen(argv[1],"r"))==NULL){
        printf("Error opening file");
        exit(-1);
    }  

    printf("Enter the number of threads: ");
    scanf("%d",&nthreads);
    threads = malloc(nthreads*sizeof(pthread_t));

    fseek(fp, 0, SEEK_END);
    len = ftell(fp);  
    printf("len= %d\n",len);

    blockSize=(len+nthreads-1)/nthreads;
    printf("size= %d\n",blockSize);

    for(id = 0; id < nthreads; id++){

        data[id].fp=fp;
        data[id].offset = blockSize;
        data[id].start = id*blockSize+1;

        }
        //LAST THREAD
        data[nthreads-1].start=(nthreads-1)*blockSize+1;

        for(id = 0; id < nthreads; id++)
            pthread_create(&threads[id], NULL, &countFrequency,&data[id]);

    for(id = 0; id < nthreads; id++)
        pthread_join(threads[id],NULL);

    fclose(fp);
    //free(threads);

    //pthread_exit(NULL);

    printf("%d\n",words); 
    return 0;  
}

【问题讨论】:

  • 除了您的错误之外,在您从磁盘中的文件读取的情况下使用多线程并不是一个好主意。您的程序性能已经受到文件读取速度的限制。
  • 在代码中加上行号会更好。

标签: c multithreading parallel-processing pthreads


【解决方案1】:

类型转换并不能修复错误代码 - 它只是伪装它或使它更加错误。让我们看看这些错误:

struct thread_data* td=(struct thread_data)data; /* wrong */

您不能将struct thread_data * 转换为struct thread_data,也不能将struct thread_data 分配给struct thread_data *。不正确的 不必要的强制转换是错误的唯一原因。

x = pthread_create(&threads[id], NULL, &countFrequency, (void *)data); /* wrong */

其次,您也不能将struct thread_data 转换为void * - 您需要一个实际的指针,例如data地址

x = pthread_create(&threads[id], NULL, &countFrequency, &data);

也没有强制转换,因为指向数据类型的指针自然会转换为void *。当然,由于data 只有一个副本,所有线程都将共享它,并且所有线程都将处理写入它的最后一个值。这不会顺利 - 每个线程需要一个 struct thread_data

第三,这些警告告诉你你的线程函数有错误的签名:

void *countFrequency(struct thread_data *data) /* wrong */

结合第一点,使所有类型都正确,并且再次不需要强制转换。

void *countFrequency(void *data) {
    struct thread_data* td = data;

【讨论】:

  • +1 您所触及的事物的一些变化构成了此处提出的所有pthreads 问题的健康部分。
  • @Notlikethat:非常感谢。我必须承认,我仍然是指针问题和线程问题的初学者。根据您的建议,我修改了我的代码,但现在出现了 Segmentation Fault。你能告诉我如何解决这个问题吗?
  • @user2015915 分配data[nthreads]nthreads 有什么值?学习使用调试器来确定故障发生的时间位置,这将在很大程度上告诉你为什么
猜你喜欢
  • 1970-01-01
  • 2017-10-01
  • 2011-12-28
  • 2011-02-02
  • 1970-01-01
  • 2016-09-19
  • 1970-01-01
  • 1970-01-01
  • 2023-03-28
相关资源
最近更新 更多