2017年10月20日
《その86》 挿入子と抽出子の多重定義(p.403演習11-2,演習11-3)
挿入子と抽出子の多重定義
今回の「挿入子と抽出子の多重定義」は、具体的には、
挿入子 << や抽出子 >> の多重定義によって、cout << や cin >> でクラスオブジェクトを扱えるようにするというものです。
【挿入子と抽出子の多重定義】
◆ 挿入子の多重定義(演算子関数 operator<< の定義)
ostream& operator<<(ostream& s, const Type& x) {
クラス x から出力したい内容を取り出すコード;
s << クラス x から取り出した出力したい内容;
return s;
}
◆ 抽出子の多重定義(演算子関数 operator>> の定義)
ostream& operator>>(ostream& s, Type& x) {
s >> 入力ストリームから読み込んだ内容を受け取るオブジェクト;
入力ストリーム s から受け取った内容をクラス x にセット;
return s;
}
※ 演算子関数の返却値がストリーム s への参照となっているので、cout << x << y; のように
連続で使用できます。
※ 引数 Type& x が参照渡しになっているのは、値渡しとのコスト的な差を考慮してのことです。
※ 演算子関数 "operator<<" の引数 "const Type& x" には "const"が付いているので、const付き
のオブジェクト等を受け取ることができます。
新版明解C++入門編 p.403 演習11-2
クラス Date 第2版に抽出子を追加せよ。
3つのファイル Date.h
Date.cpp
DateTest.cpp
を順に記述します。
// Date.h
#include <string>
#include <iostream>
class Date {
int y;
int m;
int d;
public:
Date();
Date(int yy, int mm = 1, int dd = 1);
int year() const { return y; }
int month() const { return m; }
int day() const { return d; }
Date preceding_day() const; // 前日の日付(閏年非対応)
std::string to_string() const; // 日付文字列作成
};
std::ostream& operator<<(std::ostream& s, const Date& x); // 演算子関数 operator<<
std::istream& operator>>(std::istream& s, Date& x); // 演算子関数 operator>>
// Date.cpp
#define _CRT_SECURE_NO_WARNINGS
#include <iomanip>
#include <ctime>
#include <sstream>
#include <iostream>
#include "Date.h"
using namespace std;
Date::Date() {
time_t current = time(NULL);
struct tm* local = localtime(&current);
y = local->tm_year + 1900;
m = local->tm_mon + 1;
d = local->tm_mday;
}
Date::Date(int yy, int mm, int dd) {
y = yy;
m = mm;
d = dd;
}
Date Date::preceding_day() const {
int dmax[] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };
Date temp = *this;
if (temp.d > 1)
temp.d--;
else {
if (--temp.m < 1) {
temp.y--;
temp.m = 12;
}
temp.d = dmax[temp.m - 1];
}
return temp;
}
string Date::to_string() const {
ostringstream s;
s << setfill('0') << y << "年"
<< setw(2) << m << "月"
<< setw(2) << d << "日";
return s.str();
}
ostream& operator<<(ostream& s, const Date& x) {
return s << x.to_string();
}
istream& operator>>(istream& s, Date& x) {
int y, m, d; char c;
s >> y >> c >> m >> c >> d;
x = Date(y, m, d);
return s;
}
// DateTest.cpp
#include <iostream>
#include "Date.h"
using namespace std;
int main()
{
Date x;
cout << "**/**/**形式で日付を入力:";
cin >> x; // 抽出子「 operator>> 」
cout << "日付 … " << x << '\n'; // 挿入子「 operator<< 」
}
新版明解C++入門編 p.403 演習11-3
演習11-1 で作成した時刻クラスに挿入子と抽出子を追加せよ。
3つのファイル Date.h
Date.cpp
DateTest.cpp
を順に記述します。
// Time.h
#include <iostream>
class Time {
int hour;
int minute;
int second;
public:
Time();
Time(int h, int m, int s);
int get_hour() const { return hour; }
int get_minute() const { return minute; }
int get_second() const { return second; }
void forward_h(int h);
void forward_m(int m);
void forward_s(int s);
void adjust(int &h, int &m, int &s);
};
std::ostream& operator<<(std::ostream& so, const Time& x);
std::istream& operator>>(std::istream& si, Time& x);
// Time.cpp
#define _CRT_SECURE_NO_WARNINGS
#include <iomanip>
#include <ctime>
#include <sstream>
#include "Time.h"
using namespace std;
Time::Time() {
time_t current = time(NULL);
struct tm* local = localtime(&current);
hour = local->tm_hour;
minute = local->tm_min;
second = local->tm_sec;
}
Time::Time(int h, int m, int s) {
adjust(h, m, s);
hour = h; minute = m; second = s;
}
void Time::forward_h(int h) { // hour を進める。
hour = (hour + h) % 24;
}
void Time::forward_m(int m) { // minute を進める。
m = minute + m;
adjust(hour, m, second);
}
void Time::forward_s(int s) { // second を進める。
s = second + s;
adjust(hour, minute, s);
}
void Time::adjust(int &h, int &m, int &s) {
m = m + s / 60;
s = s % 60;
h = h + m / 60;
m = m % 60;
h = h % 24;
hour = h; minute = m; second = s;
}
ostream& operator<<(ostream& so, const Time& x) {
return so << setw(2) << x.get_hour() << "時"
<< setw(2) << x.get_minute() << "分"
<< setw(2) << x.get_second() << "秒";
}
istream& operator>>(istream& si, Time& x) {
int h, m, s; char c;
si >> h >> c >> m >> c >> s;
x = Time(h, m, s);
return si;
}
// TymeTest.cpp
#include <iostream>
#include "Time.h"
using namespace std;
int main() {
Time a;
cout << "現在時刻 : " << a << '\n';
cout << '\n';
cout << "**:**:**形式で時刻を入力 : "; cin >> a;
cout << a << '\n';
a.forward_h(20) ; cout << a << "( 20時間進めました。)" << '\n';
a.forward_m(80) ; cout << a << "( 80分 進めました。)" << '\n';
a.forward_s(3700); cout << a << "( 3700秒進めました。)" << '\n';
}
--
この記事へのコメント
コメントを書く
この記事へのトラックバックURL
https://fanblogs.jp/tb/6875275
※ブログオーナーが承認したトラックバックのみ表示されます。
この記事へのトラックバック