🎯 第2回 関数と参照・オーバーロード

🏁 授業目標


🧠 関数の基本

C++の関数は、変数や処理をひとまとめにし、複数回呼び出せる便利な構造です。

関数には 宣言(プロトタイプ)定義 があり、main()より上に宣言を書き、下に定義を書くのが一般的です。

書式のイメージ:

// 関数の宣言
int add(int a, int b);
 
int main() {
int result = add(3, 5); // 呼び出し
return 0;
}
 
// 関数の定義
int add(int a, int b) {
return a + b;
} 

🧩 const参照(const &)の基本

大きなデータをコピーせずに扱う際に便利です。

const参照とは、実体のアドレスを受け取り、それを変更せずに利用する方法です。

種類 内容 特徴
値渡し 値をコピー 安全だが遅い場合もある
参照渡し 実体を直接操作 変更される可能性あり
const参照 実体を読み取り専用で参照 安全で高速

メリット

void printName(const std::string& name) {
    std::cout << "Hello, " << name << std::endl;
}
 
int main() {
std::string s = "Taro";
printName(s);          // 実体を渡す
printName("Hanako");   // 一時文字列もOK
} 

授業でやったこと

①print関数2個作る(値渡し)
②関数内で値がコピーされていることを確認
 (関数内で、値を変更しても、main側では
  変更されないよ)
③参照渡しを試してみる
 関数内で*とかつけなくても値を変更可能
 (怖い)
④const+&で引数の値を変更できなくなるよ
 ただし、コピーじゃなくアドレスで渡せる
 しかも*とかつけなくてもアクセス可能!

"main.cpp"
#include <iostream>
#include <string>
 
using std::cout;
using std::endl;
using std::string;
 
 
void printValInt(int& val);//int型引数を受け取る関数の宣言
void printName(string& name);//string型引数を受け取る関数の宣言
 
int main()
{
	int v = 42;
	string name = "Alice";
 
	printValInt(v);//int型引数を渡す
	printName(name);//string型引数を渡す
 
 
	return 0;
}
//const + &を使うことで、参照渡しの利点を活かしつつ(コピーなし)
//関数内で引数の値が変更されないようにできる
void printValInt(const int& val)
{
	//val = val + 3;
	cout << "int型の値: " << val << endl;
}
void printName(const string& name)
{
 
	cout << "名前: " << name << endl;
}

⚙️ 関数のオーバーロード

同じ名前の関数を、引数の数・型・順序の違いで複数定義できる機能です。

ポイント

int area(int w, int h) {
    return w * h;
}
 
double area(double r) {
return 3.14 * r * r;
}
 
int main() {
std::cout << area(3, 4) << std::endl; // 長方形
std::cout << area(2.5) << std::endl;  // 円
} 

🔎 const参照 + オーバーロード

L値(変数)とR値(一時オブジェクト)で利用する関数を分けることで、より安全で効率的な設計が可能です。

void print(const std::string& s) { std::cout << s << std::endl; }
void print(std::string&& s) { std::cout << s << std::endl; }
 
int main() {
std::string name = "Alice";
print(name);          // L値版関数が呼ばれる
print("Bob");         // R値版関数が呼ばれる
} 

🏆 まとめ


📁 ヘッダファイルとソースファイルの使い分け

C++では、関数を複数のファイルに分けて管理します。これによりプログラムの見通しが良くなり、再利用も容易になります。

役割の違い:

ファイル 拡張子 主な役割
ヘッダファイル .h または .hpp 関数やクラスの「宣言」だけを書く
ソースファイル .cpp 関数やクラスの「定義」(実際の処理)を書く

書き方の例:

"math.h"
// math.h
#pragma once
int add(int a, int b);
int sub(int a, int b);
"math.cpp"
// math.cpp
#include "math.h"
 
int add(int a, int b) {
return a + b;
}
 
int sub(int a, int b) {
return a - b;
} 
"main.cpp"
// main.cpp
#include <iostream>
#include "math.h"
 
int main() {
std::cout << add(5, 3) << std::endl;
std::cout << sub(5, 3) << std::endl;
} 

💡 ポイント