Part7:関数


内容


目標

関数の定義の仕方と使い方を習得する.


関数の定義と利用

これまで、標準関数と呼ばれる関数をいくつか使いました(printf 関数と scanf 関数).C言語では、自分で関数を定義し利用することができます.まずは参考書のサンプルプログラムを見てみましょう(参考書 p.120).つぎのサンプルプログラムを Part7-1.c として打ち込んでください.(いつものとおり、説明の為の行番号と、色は無視してください.)

 1: #include <stdio.h>
 2: 
 3: int beki(int a, int b);
 4:
 5: main()
 6: {
 7:     int n;
 8:
 9:     n = beki(2, 3);
10:     printf("%d\n", n);
11:
12:     printf("%d\n", beki(3, 4));
13: }
14:
15: int beki(int a, int b)
16: {
17:     int i, ans;
18:
19:     ans = 1;
20:
21:     for (i = 1; i <= b; i++)
22:     {
23:         ans = ans*a;
24:     }
25:  
26:     return ans;
27: }

青字の部分(3行目および15〜27行目)が関数の定義に関わる部分で、赤字の部分(9行目および12行目)で、定義した関数を使用している部分です.まずは定義している部分から見ていきましょう.

3行目: 関数のプロトタイプ宣言と呼ばれる宣言です.後に定義する関数の戻り値の型と、引数の型を仕様として、プログラムの先頭部分(main 関数より前)にこのように書きます.関数を定義する場合には、このプロトタイプ宣言が必ず必要だと思っておいてください.(省略する方法もありますが、この演習では必ずプロトタイプ宣言をすることとします.)

5〜13行目: main 関数の定義です.

15〜27行目: beki 関数の定義です.


戻り値引数

y = sin(x)

と書いたとき、sin が関数名で x が関数 sin の引数変数 y には sin(x) の戻り値が入ることになります.当然変数 x, y にはそれぞれ型があり、関数自体がもつ値(戻り値)にも型があります.

 先のサンプルプログラムの3行目のプロトタイプ宣言や、15行目の関数定義の部分で、 int と整数型が宣言されているのはその為です.


beki 関数の定義

 では、beki 関数の定義部分を詳しく見ましょう.15行目を見ると

int beki (int a, int b)

となっています.これは、先のプロトタイプ宣言と通常おなじ記述となります.はじめの int は、 beki 関数の戻り値の型が int であるという意味です.続いて関数名 beki があり、その後括弧に囲まれ、2つの変数が定義されています.これらは、引数として渡される値を格納する為の変数でそれらの名前をそれぞれ a, b とし、型はそれぞれ整数型としています.つまり、 beki(1,2) とこの関数が呼ばれた場合、 a には 1 が、 b には 2 が代入されることになります.

 つづいて、中括弧に囲まれた、関数本体の処理内容が続きます.この中で、新たに(この関数の定義内でのみ有効な)変数 i と ans を用意しています.さらには、先の引数部分にあった、変数 a, b が参照されています.もちろん、 a, b には関数が呼ばれた時に引数として渡されている変数の内容である数値または直接数値として渡された場合にはその数値が代入されています.

 最後の return 文により、 ans の内容が beki 関数の戻り値として返されます.

以上、関数を作る場合に必要なことをまとめると


他の例を見てみましょう.

例えば、実数値の絶対値を表示するプログラムを考えましょう.これまでの知識からプログラムは大体次のようなものになります.(以前のレポート課題)

#include <stdio.h>

main()
{
    double a;

    printf("実数を入力してください:");
    scanf("%lf", &a);

    if (a < 0.0)
    {
        a = -a;
    }

    printf("入力された実数の絶対値は %lf です.\n", a);
}

このプログラムでは、 if 文を使って絶対値を求めていますが、絶対値を求める作業が多量にある場合、いちいち if 文を書くのは面倒です.絶対値を求める関数を作ってみましょう.

#include <stdio.h>

double myabs(double f);

main()
{
   double a;

    printf("実数を入力してください:");
    scanf("%lf", &a);

    printf("入力された実数の絶対値は %lf です.\n", myabs(a));
}

double myabs(double f)
{
    if(f < 0.0)
    {
        f = -f;
    }

    return f;
}

 以前にも述べたように、自分で関数を作る場合には自由な名前をつけることができます.しかし、標準関数として既にある関数の名前をつけることはできません(例えば、printf や scanf といった関数を新たにつくることはできません).実は絶対値を求める標準関数 abs がありますので、今回は myabs という名前にしています.また、関数の名前も変数の名前の規則同様使える文字と使えない文字があります.注意してください.数字から始まらない英数字を関数名としてください.


課題1

次の仕様を満たす関数を作成し、それを使うプログラムを作成せよ.

関数名: double mymax(double a, double b)

仕様: 実数型の2つの数 a, b を受け取り、それらのうち大きい方を戻り値として返す


課題2

正の整数を1つ入力すると、その数が素数かどうかを判定して表示するプログラムを作成せよ.

ヒント: いろいろな方法があると思うが、単純な方法としては、n > 2 の整数が素数である場合には、2 <= i <= n-1 の範囲内のすべての整数 i で n を割ったときの剰余がすべて 0 以外となる.ひとつでも剰余が 0 となるのであれば n は素数ではない.剰余は % 演算子を用いることで計算できる.


課題3

次の仕様を満たす関数を作成し、それを使うプログラムを作成せよ.

関数名: int sosu(int n)

仕様: 引数として整数 n を受け取り、それが素数であれば戻り値として 1 を返し、n が素数ではないまたは負である場合には -1 を返す


課題4

課題2のプログラム(素数判定プログラム)を課題3で作った関数を使うものに変更せよ. 


今日学んだ事


戻る