Development

ITpro  > Development
Development

C言語で始めるプログラミングの基礎

日経ソフトウエア

第5回 配列を学んで文字列を処理しよう

型の変換に利用するキャスト演算子

 配列の話から少しそれますが,リスト3の割り算の前に付いている「(float)」はキャスト演算子(型変換演算子)です。hgoukeiやkgoukeiはint型(整数型)の配列で,NINZU,KYOUKAの値も整数値です。ご存じのように整数型は,小数点以下の値を持たない型です。整数型÷整数型という式は整数型の値しか返さないのですが,実際の計算結果は小数点以下の値を持つ可能性があります。そこで,キャスト演算子(float)を利用してfloat型(単精度浮動小数点型)に型を変換します。変換仕様にも%fを指定して小数点以下も表示させています。このようにキャスト演算子を使って型変換を行う方法を「明示的な型変換」と言います。

図2●リスト4の実行結果
図2●リスト4の実行結果

図3●リスト5の実行結果
図3●リスト5の実行結果

 キャスト演算子を利用しなくても型を変換することができます。これを「暗黙的な型変換」といいます。こちらは注意が必要です。リスト4のようにint型の変数値87をdouble型の変数に代入した場合はdouble型に変換され,87.000000と小数点以下に0が付きます(図2)。逆にリスト5のように,double型の変数値87.65をint型に代入した場合,小数点以下が切り捨てられ,ihenkinの値は87になります(図3)。大きなサイズの型の変数を小さなサイズの型の変数に入れると値の一部が失われることがあるので注意してください。


#include <stdio.h>
int main()
{
    int iheikin;
    double dheikin;

    iheikin = 87;
    printf("平均点は%dです\n",iheikin);
    dheikin=iheikin;
    printf("平均点は%fです\n",dheikin);

    return 0;
}
リスト4●暗黙的な型変換の例。int型の値をdouble型の変数に代入する

dheikin = 87.65;
printf("平均点は%fです\n",dheikin);
iheikin=dheikin;
printf("平均点は%dです\n",iheikin);
リスト5●リスト4と逆の例。double型の値をint型の変数に代入する

 暗黙的な型変換のルールについて,もう一つ覚えておいてほしいことがあります。異なる型どうしで計算を行うと小さいサイズのオペランド*3が大きいサイズに型変換されてから計算が行われます。リスト6では,double型のomoriとint型のkazuの掛け算しています。この場合は,int型のkazuが,double型に変換されてから計算され「重さは1.500000です」と表示されます(図4)。

#include <stdio.h>
int main()
{
    double omori;
    int kazu;

    omori = 0.5;
    kazu = 3;
    printf("%fのおもりを%d個つけると重さは%fです\n", omori,
           kazu, omori * kazu);
    return 0;
}
リスト6●double型のomoriとint型のkazuをかけ算する

図4●リスト6の実行結果
図4●リスト6の実行結果

 多次元配列の話に戻りましょう。配列のイメージは,1次元なら帯に仕切りがあるイメージです(図5)。2次元配列は面で考えるとわかりやすいでしょう。3次元配列は,トウフを味噌汁に入れるために,手の上でさいの目に切るイメージです。4次元,5次元となるとイメージするのが難しいのですが,3次元のさいの目に切った一つのさいころを一つの部屋と考え,その中に間仕切りをしていくイメージでとらえましょう。

図5●多次元配列のイメージ
図5●多次元配列のイメージ

 最後に配列について,もう一つ重要なことを説明します。リスト3の終わりにある表示部分をリスト7のように書き換えて,2次元配列tensu[i][j]の各要素が,メモリーのどのアドレスに表示されているかを表示します。アドレスを表示するにはアドレス演算子「&」を利用します。&tensu[i][j]は,tensu[i][j]が格納されるメモリーのアドレスを意味します。

for (i = 0; i < NINZU; i++) {
    for (j = 0; j < KYOUKA; j++) {
        printf("tensu[%d][%d]のアドレスは%pです\n",i,j,&tensu[i][j]);
    }
}
リスト7●配列の各要素のアドレスを表示するプログラム

 実行結果は図6です*4。Borland C++コンパイラ*5では,int型は4バイトの領域を使うので,16進数で4ずつ加算していくと,配列の各要素がメモリー上に連続して確保されていることがわかります。なぜ,配列がメモリー上に連続して確保されることが重要なのかは,次の文字列の処理を読めばわかるでしょう。

図6●リスト7の実行結果
図6●リスト7の実行結果
(金宏和實)  [2009/07/30]
出典:日経ソフトウエア 2003年11月号  pp.92-98
(記事は執筆時の情報に基づいており,現在では異なる場合があります)

この記事に対する読者コメント

コメントに関する諸注意 コメント投稿 コメント一覧