第2回

 

 

3 判断力を磨きましょう

 

制御構造の種類

 

制御構造の種類

C++言語での構文と内容

選択(条件分岐)

if      条件に応じて処理の流れを分岐させる

switch    ある整数式の値に応じて処理を多重分岐させる

無条件分岐

goto     制御の流れを無条件に変更する

 

繰り返し

while     条件式が成り立つ間繰り返す 

do while   一度は実行する while

for      カウンタ変数を用いて繰り返しを制御する

 

モジュール化

     ひとまとまりの処理に名前をつけて再利用できる

関数     ようにするとともに,他の部分で副作用が起こらない

       ように囲い込む

 

 

関係演算子

 

関係演算子

数学上の表現

C++での表現

意味

==

a == b

abが等しい

!=

a != b

abが等しくない

>=

³

a >= b

ab以上である

<=

£

a <= b

ab以下である

> 

a > b

abより大きい

< 

a < b

abより小さい

 

 


31  条件分岐(1)

 

例題31

 整数を1個入力してその整数が偶数ならば偶数と出力します.奇数の場合は,何もしません.

 

▼プログラム e3-1.cpp

 

01      // 例題31               (日付 学籍番号 氏名)

02                     // 整数を1個入力してその整数が偶数ならば偶数と出力する.

03                      

04                     #include <iostream>

05                     using namespace std;

06                      

07                     int main()

08                     {

09                       int c;

10                      

11                       cout << "整数を1個入力してください:";

12                       cin >> c;

13                      

14                       if (c % 2 == 0) {

15                         cout << c << " は偶数です" << endl;

16                       }

17                      

18                       return 0;

19                     }

 

 

練習問題31

例題31で,ifの条件部分をif (1 == c % 2)と変えてみましょう.

 

 

練習問題32

例題31で,ifの条件部分をif (c % 2 = 1) と変えてみましょう.

 

 

練習問題33

例題31で,整数dを宣言し,ifの条件部分をif (d = c % 2) と変えてみましょう.

 

 

練習問題34

次のプログラムは,整数nが1かどうかチェックするプログラムです.正しく動くでしょうか.正しく動かないとするとなぜでしょうか.

    if (n = 1) {

          cout << "1です" << endl;

        }

 

同様に,次のプログラムは,整数n0かどうかチェックするプログラムです.正しく動くでしょうか.正しく動かないとするとなぜでしょうか.

    if (n = 0) {

          cout << "0です" << endl;

        }

     

 

練習問題313

2個の整数abの値をキーボードから入力して,次の4つの条件式

(1)    a == b

(2)    a != b

(3)    a >= b

(4)    a <= b

の評価値を出力するプログラムを作成してみましょう.

 

 

練習問題314

以下のプログラムをコンパイル(して,もし可能ならば実行)してみてください.

    if (n = a < b) {

          cout << "abより小さい" << endl;

        }

        cout << "nの値は " << n << " です" << endl;

 

 

 

32  条件分岐(2)― 条件が成り立たなかった場合

 

例題32

 例題31を変更して,整数を1個入力してその整数が奇数ならば「奇数です」,偶数ならば「偶数です」と出力するプログラムを作成してみましょう.

 

▼プログラム e3-2.cpp

 

01      // 例題32               (日付 学籍番号 氏名)

02                     // 整数を1個入力してその整数が奇数ならば奇数,偶数ならば偶数と出力する.

03                      

04                     #include <iostream>

05                     using namespace std;

06                      

07                     int main()

08                     {

09                       int c;

10                      

11                       cout << "整数を1個入力してください:";

12                       cin >> c;

13                      

14                       if (c % 2 == 1) {

15                         cout << c << " は奇数です" << endl;

16                       } else {

17                         cout << c << " は偶数です" << endl;

18                       }

19                      

20                       return 0;

21                     }

 

 

 


練習問題315

以下のプログラムは,英語の大文字であるかどうかを調べるためのものです.大文字の場合は「大文字です」,それ以外の場合は「大文字ではありません」と出力します.正しく動いているか(a % を入力して)確認してください.正しく動かないとしたら,正しく動くように修正してみましょう.

 

   #include <iostream>

      using namespace std;

 

      int main()

      {

        char ch;

   

        cout << "文字を入力してください:";

        cin >> ch;

        if (ch >= 'A')

          if (ch <= 'Z')

            cout << ch << " は大文字です" << endl;

        else

          cout << ch << " は大文字ではありません" << endl;

 

     return 0;

      }

 

 

練習問題318

以下のプログラムを実行して,何が起こっているか考えましょう.

  i = 0;

    if (i++ > 0) {

      cout << i << " > 0" << endl;

    } else {

      cout << i << " <= 0" << endl;

    }

 

i++ ++i に変更するとどうなるでしょう。

 

 

 

練習問題320

 整数nを読み込んで,その逆数1/nを浮動小数点型で出力するプログラムを書いてみましょう.0が入力されたら,"計算不能です"と表示して終了しなさい.

 

 

練習問題321

次のプログラムを実行してみましょう.

 

   #include <iostream>

      using namespace std;

 

      int main()

      {

        double a = 0.0000001, b = 0.0001;

       

        if (a == b / 1000.0) {

cout << "OK" << endl;

          } else {

            cout << "NO" << endl;

          }

          cout << "a - b / 1000.0 = " << a - b / 1000.0 << endl;

          return 0;

        }

 

     

注.浮動小数点型の誤差に注意すること.特に,小数点以下は2進数で表現されるので,

  例えば,

0.1    = 0×2-1 + 0×2-2 + 0×2-3 + 1×2-4 + …

   といった無限小数表現となってしまう.

 

 


33  条件分岐(3)― 複雑な条件分岐

 

例題33

 文字を読み込んで,その文字が英語の文字かそれとも数字かを判定するプログラムを作成してみましょう.

 

▼プログラム e3-3.cpp

 

01      // 例題33               (日付 学籍番号 氏名)

02                     // 文字を読み込んでその文字が英語文字かそれとも数字かを判定する.

03                      

04                     #include <iostream>

05                     using namespace std;

06                      

07                     int main()

08                     {

09                       char ch;

10                       

11                       cout << "文字を一文字入力してください:";

12                       cin >> ch;

13                       

14                       if ((ch >= 'a' && ch <= 'z') || (ch >= 'A' && ch <= 'Z')) {

15                         cout << "英語の文字です." << endl;

16                       } else if (ch >= '0' && ch <= '9') {

17                         cout << "数字です." << endl;

18                       } else {

19                         cout << "英数字以外の文字です." << endl;

20                       }

21                      

22                       return 0;

23                     }

 

 


《演算子の優先度と結合順序》

 

演算子

結合規則

スコープ解決   ::

関数呼び出しなど ()  []  ->  .

単項       !  ~  ++  --  +  -  *  &  (type)  sizeof

         new  delete

乗法       *  /  %

加法       +  -

ビットシフト   <<  >>

関係       <  <=  >  >=

等価       ==  !=

ビットand    &

ビットxor    ^

ビットor     |

論理and     &&

論理or      ||

条件       ?:

代入       =  +=  -=  *=  /=  %=  >>=  <<=  &=  ^=  |=

コンマ      ,

 

 

右から左

 

 

 

 

 

 

 

 

 

 

 

右から左

右から左

 

 

 

 

注1.   演算子の優先関係は迷ったら,()を用いて明示するようにしましょう.

注2.   論理演算子&&では,左右のオペランドは必ず評価されるが,論理演算子||では,左オペランドをまず評価してそれが真の場合は右オペランドは評価されない,ことをしっかり覚えておきましょう.

注3.   コンマ演算子は2項演算子で,評価値として右オペランドの値を返します.

 

 


練習問題322

次のプログラムを実行してみて何が起こっているか確認してみましょう.i0を入力したり,1を入力してみてください.

 

if (!i == 0) {

cout << i << " 0ではありません." << endl;

} else {

cout << i << " 0です." << endl;

}

 

 

 

練習問題323

次のプログラムを実行するとどうなるでしょうか.

 

i = j = 0;

if (i = 5 || j = 4) {

cout << i << ", " << j << endl;

}

 

 

練習問題324

次のプログラムを実行するとどうなるでしょうか.

 

i = j = 4;

if (i == 5, j == 4) {

cout << i << ", " << j << endl;

}

 


練習問題325

次のプログラムを実行してみて何が起こっているか確認してみましょう.

 

i = -1;

j = -2;

if ((i = 5) || (j = 4)) {

cout << i << ", " << j << endl;

}

if ((i = 0) || (j = 4)) {

cout << i << ", " << j << endl;

}

 

 

練習問題329

a, b0, 10が偽,1が真)の値を取るブール型の変数とします.このとき,a, bの間の2項論理演算NAND, NOR, XORを表す演算を論理演算子を用いて定義して,a, bの値を入力するとNAND, NOR, XORの値を計算して出力するプログラムを作成してみましょう.

 

▼出力例

 ブール値aを入力してください: 1

 ブール値bを入力してください: 0

 a = 1, b = 0

 NAND = 1

 NOR = 0

XOR = 1

 

 

練習問題330

小数点以下第3桁で四捨五入して,小数点以下第2位までの浮動小数点に変換するプログラムを作成してみましょう.負の数にも対応できるようにしなさい.特に小数点以下の0がうまく表示できるように注意しましょう.例えば, -3.9951を入力すると-4.00を出力します.但し,#include <iomanip> による書式設定の関数は用いないこと.

 

 

 


3.4  条件分岐(4)

 

例題34

 何月かを表す整数を読み込んで,その月が何日あるかを出力するプログラムを作成してみましょう.

 

▼プログラム e3-4.cpp

 

01      // 例題34               (日付 学籍番号 氏名)

02                     // 何月かを読み込んで,その月が何日であるかを出力するプログラム

03                      

04                     #include <iostream>

05                     using namespace std;

06                      

07                     int main()

08                     {

09                       int month, day;

10                       cout << "何月ですか?";

11                       cin >> month;

12                       

13                       switch (month) {

14                         case 2: day = 28;  // うるう年は考えない

15                                 break;

16                         case 4:

17                         case 6:

18                         case 9:

19                         case 11:  day = 30; // 小の月

20                                   break;

21                         case 1:

22                         case 3:

23                         case 5:

24                         case 7:

25                         case 8:

26                         case 10:

27                         case 12:  day = 31; // 大の月

28                                   break;

29                         default:  cout << month << "月はありません" << endl;

30                                   return 1;

31                       }

32                       cout << month << "月は" << day << "日です." << endl;

33                       return 0;

34                     }

 

 

 

練習問題331

例題34caseラベルで,定数式である数値リテラルのかわりに,式(たとえば,変数dayや,day - 1といった式)を使ってみるとどうなるでしょう.

 

 

練習問題335

13の整数を読み込み,それをローマ数字(T, U, V)に変換するプログラムを作成してみましょう.VはIを3回出力するように,“串刺し実行”で実現してみましょう.

 

 


35  数学関数群

 

例題35

 数を入力すると,その平方根を求めるプログラムを作成してみましょう.

 

▼プログラム e3-5.cpp

 

01      // 例題35               (日付 学籍番号 氏名)

02                     // 数を入力するとその平方根を求める

03                      

04                     #include <iostream>

05                     #include <cmath>

06                     using namespace std;

07                      

08                     int main()

09                     {

10                       double a;

11                       cin >> a;

12                       cout << a << "の平方根は" << sqrt(a) << endl;

13                       return 0;

14                     }

 

 

 

《よく使われる数学関数》

sin(x)    xの単位はラジアン

cos(x)

atan2(y, x)  y/xarctangent

exp(x)    指数関数 ex

log(x)    xの自然対数(基数はe)(x > 0

log10(x)   xの常用対数(基数は10)(x > 0

pow(x, y)   xy

sqrt(x)

fabs(x)    xの絶対値

ceil(x)    x以上の最小の整数値

floor(x)   x以下の最大の整数値

 

 

 

36  時刻と日付

 

例題36

 現在の日付を西暦で,たとえば,2003924日と表示するプログラムを作成してみましょう.

 

▼プログラム e3-6.cpp

 

01      // 例題36               (日付 学籍番号 氏名)

02                     // 現在の日付,時刻を求めるための機能をチェックする

03                     #include <iostream>

04                     #include <ctime>

05                     using namespace std;

06                      

07                     int main()

08                     {

09                       time_t now;  // time_t型の変数としてnowを定義する

10                       time(&now);  // これで,nowに現在時刻が入る

11                       tm     *np;  // tmという型(構造体)へのポインタを設定する

12                       np = localtime(&now);  // これで日本時間に変換される

13                       int year, month, day, hour, minute, second;

14                       

15                       year = np->tm_year + 1900; // 西暦年がセットされる

16                       month = np->tm_mon + 1;    // 月の値(011)なので1足す

17                       day = np->tm_mday;         // 日の値(131

18                       hour = np->tm_hour;        // 現在時刻の時(123

19                       minute = np->tm_min;       // 現在時刻の分(159

20                       second = np->tm_sec;       // 現在時刻の秒(159

21                       cout << year << "" << month << "" << day << "" << endl;

22                       return 0;

23                     }

 

 


練習問題338

現在の時刻を,たとえば,13:05と表示するプログラムを作成してみましょう.

 

 

練習問題339

現在の時刻を,たとえば,1:05 PM と表示するプログラムを作成してみましょう.

 

 

練習問題340

今日の日付,時間,曜日を次のように表示するプログラムを作成してみましょう.

 20030924日 4:05 PM

 今日は水曜日です.

 

《ヒント》例題36で,np->tm_wdayを用いると曜日(06で日曜から土曜に対応)が得られます.曜日の名前を配列で用意して表示してみましょう.月日,時刻をそれぞれ2桁表示で頭に0を付加するには,#include <iomanip> を行い,適当な入出力マニピュレータを調べて使用しなさい。

 

 

 

 

練習問題341

 下記のa)d)に示した出力を行うように,次に示したコード断片を変更してください.但し,大カッコを挿入する以外の変更を行ってはいけません.また,変更が必要でない場合もありえます.解答は,それぞれ字下げを行って見やすい形で示しなさい.

 

  if (y == 8)

    if (x == 5)

    cout << "@@@@@" << endl;

    else

    cout << "#####" << endl;

    cout << "$$$$$" << endl;

    cout << "&&&&&" << endl;

 

a)     x = 5, y = 8と仮定すると,次のように出力する.

@@@@@

$$$$$

&&&&&

b)     x = 5, y = 8と仮定すると,次のように出力する.

@@@@@

c)     x = 5, y = 8と仮定すると,次のように出力する.

@@@@@

&&&&&

d)     x = 5, y = 7と仮定すると,次のように出力する.

#####

$$$$$

&&&&&

 

 

 

練習問題342

 伝説によれば,1626年にPeter Minuit氏は24ドルでマンハッタン島を購入したという.彼は果たして良い買い物をしたのであろうか?この問題に答えるため,複利計算プログラムを作成しなさい.そして,元金24ドルからスタートして2003年(377年間)における元利合計を計算してみましょう.具体的に,年利率を5%,6%,7%,8%,9%,10%とした場合の計算結果(億ドルを単位に小数点以下2桁まで)を示しなさい.

 《ヒント》数学関数powを用いなさい.その場合,#include <cmath> が必要です.

   表示をそろえたり,小数点以下2桁まで示したりするための書式設定には

   #include <iomanip> を行い,適当な入出力マニピュレータを調べて使用しなさい。

 

▼出力例

 

年利率()     元利合計(億ドル)

   5                        23.37

6                       832.76

7