● case文で範囲指定を使用する
caseラベルにおいて連続した値の範囲を指定することができます.
case low ... high:
この例は,low以上high以下の個々の整数値について,個別にcaseラベルを記述するのと同等の効果をもちます.これは便利に使用できると思います.ANSI Cの仕様にこだわらないならば,可搬性を犠牲にして,可読性を取るのも良いと思います.
リスト25〜リスト28に示すように,case文で範囲指定を使用したほうが可読性も上がり,またアセンブラからわかるように速度も改善されると思います.
もっとも,リスト29のような条件の場合には,default文を使ったほうがコードは小さくなります.ただし,この記法では,dataの値が2,3,4,5の場合に何をするのかが一目ではわかりません.
〔リスト29〕default文を使った例(test64.c)
|
#include <stdio.h>
int main(void)
{
int temp;
int data;
switch ( data )
{
case 1:
temp = 5;
break;
case 6:
temp = 10;
break;
default:
temp = 9;
}
return;
}
|
|
● 共用体へのキャスト
以下のような定義があるとします.
union foo { int i; double d; };
int x;
double y;,
この場合,
(1) u = (union foo) x
(2) u.i = x
(3) u = (union foo) y
(4) u.d = y
の(1)と(2),(3)と(4)が等価になります.
共用体へのキャストを関数への引き数として使うことも可能です.この仕様は,生成関数式から派生しています.これを使うことは,可読性という面に関しては有益でしょう.
リスト31〜リスト34に例を示します.アセンブラを比較すると,微妙にANSI C準拠のコードのほうがコンパクトになっています.共用体へのキャストを使用したほうのアセンブラで,1行増えた原因となっているコード,
movl %edx,-4(%ebp)
は不要であるような気がします.これは,最適化したら改善されました(リスト35).
〔リスト35〕最適化してアセンブルした結果(test67.s)
|
.file "test67.c"
.version "01.01"
gcc2_compiled.:
.comm x,4,4
.comm y,8,8
.text
.align 4
.globl main
.type main,@function
main:
pushl %ebp
movl %esp,%ebp
movl $10,x
movl %ebp,%esp
popl %ebp
ret
.Lfe1:
.size main,.Lfe1-main
.ident "GCC: (GNU) 2.95.3 20010315 (release)"
|
|
|