2004 年度「計算機基礎論3B」 レポート問題

いずれも、プログラミング言語としては C 言語を用い、 特に指定のないものについてはメールでソースファイルのみを提出させた。

課題1

あなたのユーザ id の下二桁を(十進整数とみて) 100 で割ったものに 1 を加えた数を公比とし、 ユーザが入力した数を初項とする等比数列の初めの 10 項について、 「第…項めは…です」のように出力するプログラムを書きなさい。

課題2

適当な十進二桁の素数 p を一つ選び、 1 以上 p 未満の自然数 x に対し mod p での逆数を返す関数 int inv(int x) を書け。 すなわち、 積 xy が mod p で 1 になるような自然数 y を返す関数を書け。 y は 1 以上 p 未満に値をとるようにせよ。

main() もつけて提出すること。 main() をどんなふうに書くかは各自の判断に任せる。

課題3(に準ずるもの)

次のプログラムの末尾に関数 void print(void) を自分で書いてつけ加えよ。 ただし、この関数は、 配列に格納されている値をスペースで区切って一行に出力するものとする。 値は 0 以上 100 未満なので、 一桁のときも二桁分のスペースで出力されるようにせよ。 そのとき、十の位を 0 とするかスペースにするかは各自の判断にまかせる。 定数 N の値は、 Terminal を最大にしたうえでなるべく大きくしておくとよいだろう。

#include <stdio.h>
#include <stdlib.h> /* srand() */
#include <time.h>   /* time() */

#define N 20

void init(void);
void print(void);

int a[N];

int main() {
    init();
    print();

    return 0;
}


void init(void) {
    int i;

    srand((unsigned)time(NULL));    /* 現在時刻で乱数の種を初期化 */
    for (i = 0; i < N; i++) {
        a[i] = rand() % 100;
    }
    return;                         /* この return は普通は書かない */
}

/* ここに書き加える */

関数 void swap(int i, int j) を書き加えよ。 この関数は、a[i]a[j] の値を入れかえるものとする。 (ヒント:前に見せた、うまく動作しない swap() を参考にせよ。 最初は ij は等しくないと仮定して書いてみて、 書けたものが ij が等しいときも OK かどうかを考えよ。)

関数 int max(int i, int j) を書き加えよ。 この関数は、a[i], a[i+1], ..., a[j-1], a[j] のうちで最大の値をもつものの添字を返すものとする。 (たとえば、 もしも a[8] が最大でその値が 15 なら、8 を返す。 15 ではない。 最大の値をもつものが複数あるときはどれを返してもよい。 ij が等しいときも正しく動作しなければならないことに注意。 配列に格納されている値に上限・下限があることを利用してはいけない。)

ここまでに書いた関数を組み合わせて、 次のようにして配列をソートするプログラムを書いてみよ。

メールで提出する課題とはしませんが、 あとで私が諸君のホームディレクトリを見て調べ、 課題1や2と同じぐらいのウェイトで成績に加算します。 (全部やってなくても、それなりに取り組んだことがわかれば OK です。)


岩瀬順一