5

これが1か月のリマインダーリストを印刷するプログラムです。これはKNキングの本からの例です。私の問題は、このプログラムでstrcmp関数がどのように機能するかを理解できないことです。

#include <stdio.h>
#include <string.h>

#define MAX_REMIND 50       /* Maximum number of reminders */
#define MSG_LEN 60          /* max length of reminders message */

int read_line(char str[], int n);

int main(void) {
    char reminders[MAX_REMIND][MSG_LEN+3];
    char day_str[3], msg_str[MSG_LEN+1];
    int day, i, j, num_remind = 0;

    for(;;) {
        if(num_remind == MAX_REMIND) {
            printf("--No space left--\n");
            break;
        }

        printf("Enter day and reminder: ");
        scanf("%2d", &day);
        if(day == 0)
            break;
        sprintf(day_str, "%2d", day);
        read_line(msg_str, MSG_LEN);

        for(i = 0; i < num_remind; i++)
            if(strcmp(day_str, reminders[i]) < 0)
                break;

        for(j = num_remind; j > i; j--) 
            strcpy(reminders[j], reminders[j - 1]);

        strcpy(reminders[i], day_str);
        strcat(reminders[i], msg_str);

        num_remind++;
    }

    printf("\nDay Reminder\n");
    for(i = 0; i < num_remind; i++)
        printf(" %s\n", reminders[i]);

    return 0;
}

int read_line(char str[], int n) {
    int ch, i = 0;
    while((ch = getchar()) != '\n')
        if (i < n)
            str[i++] = ch;

    str[i] =  '\0';
    return i;
}

私が理解したのは、文字列は2D配列に格納されており、すべての行がユーザーからの文字列を受け入れるということです。プログラムは最初に日付(ユーザーから小数点以下2桁)を取得し、sprintf()関数を使用して文字列に変換します。次に、変換された文字列の日付を、reminder[][]配列に格納されている文字列と比較します。

日付と文字列を比較する方法がわかりません。(その場合は常にtrueを返し、毎回i = 0でステートメントを中断します)。

4

2 に答える 2

2

このコードで使用されているstrcmpは、ソートに使用されます。デバッグコードを追加すると(27行目以降)、strcmpによってどのような結果が生成されるかがわかります。

for(i = 0; i < num_remind; i++) {
    printf("%s comparing to %s is %d \n", day_str, reminders[i], strcmp(day_str, reminders[i]));
    if(strcmp(day_str, reminders[i]) < 0) {
            break;
    }
}

ご覧のとおり、新しく入力されたday_strが、保存されたリマインダーの先頭から他のリマインダーよりも小さい場合、 forループが中断されます。この方法で取得したiは、次のforループで使用され、保存されているすべてのリマインダーをnum_remindからiにそれぞれ1桁ずつ(最後の要素からiに)シフトします。最後に、これらの2行は、day_strとmsg_strを正しい場所に配置しています。

strcpy(reminders[i], day_str);
strcat(reminders[i], msg_str);

この種のソートを理解するには、この挿入ソートを見てください。

于 2013-03-09T16:08:27.863 に答える
1

'day'変数は整数であり、 "%2d"の形式の文字列で構成されているため、数値6は"6"になります。

次に、プログラムはリマインダーをループし、次の条件で中断します。

if(strcmp(day_str, reminders[i]) < 0)

ここではstrcmpを使用して、day_strの文字列がreminders[i]の文字列よりも早くソートされるかどうかを判断しています。

したがって、reminders[]配列は日数の昇順で並べ替えられます。このループは、新しいデータの挿入ポイントで中断されます。次に、既存のすべてのリマインダーを配列内の1つの位置に移動し、新しいデータを挿入するためのスペースを確保します。

于 2013-03-09T16:09:06.400 に答える