
C言語基礎|汎用的な関数
同じ“部品”でいろんな仕事をさせよう
前の記事では、決まった記号を並べるだけの関数を作って、三角形表示の見通しを良くしましたよね。
ここで一歩進めて、もっと使い回せる関数(汎用的な関数)にしてみましょう。
「同じ処理を、ちょっと条件を変えて何回も使いたい」
これ、プログラミングあるあるです。そこで登場するのが、引数で動作を切り替えられる関数です。

汎用的な関数って何?
ざっくり言うと、
- 特定の用途だけに固定されていない。
- 引数を変えるだけで別の用途にも使える。
- いろんな場所で再利用できる。
そんな関数のことです。
専用関数と汎用関数の違い
| 種類 | できること | 例 | 便利さ |
|---|---|---|---|
| 専用関数 | 目的が固定 | 星だけを並べる | 使う場面が限られる |
| 汎用関数 | 引数で用途を変えられる | 文字と回数を渡して並べる | いろんな場面で使える |
「星専用」から「好きな文字でOK」に変えるだけで、利用シーンが一気に広がります。
サンプルプログラム
ここでは タイトル付きの枠(フレーム)を描くプログラムを例にして、汎用関数の強みを体感します。
- repeat_char:指定した文字を指定回数だけ表示する(汎用的)
- draw_box:repeat_charを使って枠を描く(再利用の例)
プロジェクト名:chap6-8-1 ソースファイル名:chap6-8-1.c
Visual Studio でこのプログラムを実行するには、SDLチェック設定を変更しておく必要があります。
1.プロジェクト名を右クリックして、「プロパティ」をクリックします。
2.「C/C++」→「全般」→「SDLチェック」を「いいえ」に切り替えて「OK」をクリックします。
#include <stdio.h>
// 指定した文字chをn個連続して表示(値は返さない)
void repeat_char(int ch, int n)
{
while (n-- > 0)
putchar(ch);
}
// 幅widthのシンプルな枠を表示する
void draw_box(int width)
{
// 上辺
putchar('+');
repeat_char('-', width);
putchar('+');
putchar('\n');
// 中身(空行)
putchar('|');
repeat_char(' ', width);
putchar('|');
putchar('\n');
// 下辺
putchar('+');
repeat_char('-', width);
putchar('+');
putchar('\n');
}
int main(void)
{
int w;
puts("タイトル枠を表示します。");
printf("横幅を入力してください:");
scanf("%d", &w);
puts("----- 表示例 -----");
draw_box(w);
puts("同じ部品を使って、別の線も引けます。");
repeat_char('=', w + 2);
putchar('\n');
return 0;
}実行例
タイトル枠を表示します。
横幅を入力してください:10
----- 表示例 -----
+----------+
| |
+----------+
同じ部品を使って、別の線も引けます。
============repeat_char は枠の横線にも、空白にも、最後の強調線にも使えています。
これが「汎用性」の気持ちよさです。
汎用関数は“道具箱のドライバー”
引数で動作が変わる
| 入力(引数) | repeat_charがすること | 出力 |
|---|---|---|
| ch = '-' , n = 10 | - を10回表示 | ---------- |
| ch = ' ' , n = 10 | 空白を10回表示 | (空白10個) |
| ch = '=' , n = 12 | = を12回表示 | ============ |
同じ関数でも、引数が変わるだけで仕事が変わります。
表の説明(この記事で使ったものの補足)
- 「専用関数と汎用関数の違い」表
→ 目的が固定されているか、引数で切り替えられるかを整理しました。汎用化すると、同じ関数を別の表示にも流用できるのがポイントです。 - 「引数で動作が変わる」表
→ repeat_char が、文字chと回数nという2つの入力で動作を決めていることを示しました。ここが汎用化の核心です。
登場する命令の書式と役割
repeat_char の定義(書式)
- void 関数名(引数...) { 文; }
例
- void repeat_char(int ch, int n) { ... }
これは「値を返さず、表示処理だけをする関数」です。
while の書式
- while(条件) 文
例
- while (n-- > 0) putchar(ch);
意味:n が 0 より大きい間、putchar(ch) を繰り返す
putchar の書式
- putchar(文字)
文字を1つ表示します。repeat_char がこれを何度も呼んで「連続表示」を作っています。
puts の書式
- puts(文字列)
文字列を表示して改行します。見出し表示に便利です。
scanf の書式
- scanf(書式, 変数のアドレス)
キーボード入力を読み込みます。今回だと width を読むために使っています。
よくある注意点(汎用関数でハマりやすいところ)
ありがちな落とし穴
| 注意点 | 何が起きる? | 対策 |
|---|---|---|
| 回数nが負になる | 繰り返しが1回も動かない、または意図不明になる | 入力チェックを入れる |
| 幅が小さすぎる | 枠が崩れる | 最低値を決める(例:1以上) |
| chをcharにしてもOK? | putcharはintを受ける設計 | 引数はintにしておくと安心 |
演習問題
演習6-6:合図をn回表示する関数を作ろう
指定した文字を n 回表示して改行する関数を作成せよ。
- 関数名:signal_n
- 返却値型:void
- 引数:int ch, int n
プロジェクト名:chap6-8-2 ソースファイル名:chap6-8-2.c
Visual Studio でこのプログラムを実行するには、SDLチェック設定を変更しておく必要があります。
1.プロジェクト名を右クリックして、「プロパティ」をクリックします。
2.「C/C++」→「全般」→「SDLチェック」を「いいえ」に切り替えて「OK」をクリックします。
#include <stdio.h>
void signal_n(int ch, int n)
{
while (n-- > 0)
putchar(ch);
putchar('\n');
}
int main(void)
{
puts("合図を表示します。");
signal_n('!', 5);
signal_n('#', 8);
return 0;
}解説
repeat_char と同じ発想で、文字と回数を引数にすると、!でも#でも同じ関数で表示できます。これが汎用関数の基本形です。
まとめ:汎用性を上げるコツ
- 固定値をやめて、引数で渡す(文字、回数、幅など)
- 小さな処理を部品化して、他の関数から呼び出す。
- 同じ処理が2回出たら、汎用関数のチャンス
