1

次のコードがあります

typedef struct 
{
    char word[64];
} DataStructure;

sigset_t set;
FILE *pFile;

static void *print(void *ptr)
{
    char *message;
    message = (char *)ptr;
    int sig;

    while(!feof(pFile))
    {
        sigwait(&set, &sig);
        printf("%s \n", message);
        sleep(2);
    }
    return 0;
}

int main(int argc, char *argv[])
{
    DataStructure Data;

    sigemptyset(&set);
    sigaddset(&set, SIGUSR1);
    pthread_sigmask(SIG_BLOCK, &set, NULL);

    pthread_t thread;
    pthread_create(&thread, NULL, print, (void *)Data.word);

    pFile = fopen("rhyme1.txt", "r");

    while(!feof(pFile))
    {
        fscanf(pFile, "%s", Data.word);
        pthread_kill(thread, SIGUSR1);  
    }

    pthread_join(thread, NULL);
    pthread_exit(NULL);
}

/*The output should look like:
Hickory,
dickory,
dock,
The
mouse
ran 
up
the
clock.

This code results in:
clock. */

テキスト ファイルを開いて、scanf を使用して行の各単語を読み取ろうとしています。次に、単語は「print」メソッドに送信され (pthread_create のパラメーターを介して)、シグナルが送信されると (pthread_kill を介して) 読み込まれた単語が出力されます。このプロセスは、ファイルが完全に読み込まれて印刷されるまで繰り返されます。

4

2 に答える 2

2

まさにダックが提案したもの。

できることは、読み取り用に 1 つのスレッドを使用し、印刷用に 1 つのスレッドを使用することです。各スレッドは、同期を維持するために互いにシグナルを送信します。

static void *print(void *ptr)
{
    char *message = (char *)ptr;
    int sig;

    while(!feof(pFile))
    {
        sigwait(&set, &sig);
        printf("%s\n", message);
        pthread_kill(thread2, SIGUSR1);  
    }


    return 0;
}
static void *readstr(void *ptr)
{
    char *message = (char *)ptr;
    int sig;

    while(!feof(pFile))
    {
        fscanf(pFile, "%s", message);
        pthread_kill(thread1, SIGUSR1);  
        sigwait(&set, &sig);
    }

    return 0;
}
于 2012-11-01T01:56:03.847 に答える
0

スレッド内のループが実行される前に複数回オーバーライドされる Data.word へのポインターを渡しているため、「クロック」になります。「時計」は、その記憶場所にある最後のものに発生します。

while(!feof(pFile))
{
    fscanf(pFile, "%s", Data.word);
    pthread_kill(thread, SIGUSR1);  
}

上記は、おそらくスレッドが実行される前、そして確実に 2 秒間のスリープが終了する前に、ファイルをすばやくめくります。

while(!feof(pFile))
{
    sigwait(&set, &sig);
    printf("%s \n", message);
    sleep(2);
}

その後の実行で異なる結果が得られる可能性がありますが、期待どおりになるとは思えません。シグナルはキューに入れられません。

于 2012-11-01T01:52:05.167 に答える