アフィリエイト広告を利用しています

広告

posted by fanblog

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<< 」
}

c11_02.png



新版明解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';
}

c11_03.png


新版 明解C 入門編 (明解シリーズ)

新品価格
¥2,916から
(2017/8/30 21:02時点)









--
この記事へのコメント
コメントを書く

お名前:

メールアドレス:


ホームページアドレス:

コメント:

※ブログオーナーが承認したコメントのみ表示されます。

この記事へのトラックバックURL
https://fanblogs.jp/tb/6875275
※ブログオーナーが承認したトラックバックのみ表示されます。

この記事へのトラックバック

 たまに、クリック お願いします m(_ _)m

 AA にほんブログ村 IT技術ブログ C/C++へ

こうすけ:メール kousuke_cpp@outlook.jp

【1】★★C++ 記事目次★★ ← 利用可能です。
・新版明解C++入門編 / 新版明解C++中級編
・その他 C++ 関連記事

【2】★★こうすけ@C#★★
・C# の初歩的な記事


検索
<< 2018年08月 >>
      1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30 31  
プロフィール
こうすけさんの画像
こうすけ

 たまに、クリック お願いします m(_ _)m

 AA にほんブログ村 IT技術ブログ C/C++へ

こうすけ:メール kousuke_cpp@outlook.jp

【1】★★C++ 記事目次★★ ← 利用可能です。
・新版明解C++入門編 / 新版明解C++中級編
・その他 C++ 関連記事

【2】★★こうすけ@C#★★
・C# の初歩的な記事


×

この広告は30日以上新しい記事の更新がないブログに表示されております。