第 3 回 文字列

本日の内容


このドキュメントは http://edu.net.c.dendai.ac.jp/ 上で公開されています。

3-1. 前回の演習の復習

合計

与えられた配列変数全ての和を求めるには、一つ一つの配列変数の値を 足していく必要があります。 配列変数 a[i] の値を合計するとし、 goukei という変数を用意したとします。 今、 i-1 番目までの合計がこの変数に合計されていたとすると、i 番目の値 a[i] だけこの goukei 変数を増やして上げれば i 番目の値までの合計が求ま ることになります。 つまり goukei = goukei + a[i] とすれば良いことになります(C 言語では goukei += a[i] と書くことができます)。 これを i = 0 から配列の終りまでやれば合計が求まることになります。


#include <stdio.h>
main(){
  int a[]={5, 2, 6, 3, 1, -1};
  int i,goukei;
  goukei=0;
  for(i=0;a[i]!=-1;i++){
   goukei += a[i];
  }
  printf("合計 %d\n",goukei);
}

キャスト

整数の値の平均を求めることを考えます。 整数の値の合計は整数ですし、個数も整数です。 しかし、(平均)=(合計)/(個数)は一般には整数の値ではなく、小数点付きの値 が求められます。 ところが、 C 言語では、(整数)/(整数) の値は小数点以下を切り捨てた整数 になります。 従って、次のプログラムでは正しく答が求められないことになります。


#include <stdio.h>
main(){
  int a[]={5, 2, 6, 3, 1, -1};
  int i,goukei,k;
  goukei=0;
  for(i=0;a[i]!=-1;i++){
   goukei += a[i];
   k++
  }
  printf("平均 %f\n",goukei/k);
}

そこで、(整数)/(整数) が整数でないようにします。 それには(浮動小数点)/(整数) となるようにすれば良いです。 つまり、式において整数型の変数を浮動小数点型に読み替えられれば、目的の 計算が出来ます。 このように、変数や式の値を別の型に指定することをキャストと呼び、 次のように式の前に () で括った型の名前を書きます。


(型)式

上のプログラムの場合、 goukei/k の goukei を float に指定したいので、 (float) goukei/ k と書きます。 書き直したプログラムは次のようになります。


#include <stdio.h>
main(){
  int a[]={5, 2, 6, 3, 1, -1};
  int i,goukei,k;
  goukei=0;
  for(i=0;a[i]!=-1;i++){
   goukei += a[i];
   k++
  }
  printf("平均 %f\n",(float) goukei/k);
}

3-2. 文字列

C 言語では文字列は文字の配列として扱います。 また、その文字配列の一番最後に番兵として特殊な文字 '\0' という要素を必 ず入れます。 例えば、 abc という文字列を配列 x[4] に入れる時は、次のようになります。


char x[4]={'a','b','c','\0'};

但し、この {'a','b','c','\0'} は単純に "abc" と書くことができます。従っ て、次のように宣言することができます。


char x[]="abc";

このように宣言すると x[0]='a', x[1]='b', x[2]='c', x[3]='\0' となりま す。

一文字を printf で表示するには %c を使いますが、配列変数に入っている文 字列全部を出力するには %s を使用します。 文字列全部と、それを左から一文字ずつ印刷するには次のようにします。


#include <stdio.h>
main(){
  char x[]="abc";
  int i;
  for(i=0;x[i]!='\0';i++){
    printf("文字列 %s の %d 番目は %c\n",x,i,x[i]);
  }
}

3-3. 文字コード

コンピュータでは文字を取り扱うため、数字を割り当てています。 これを文字コードと言います。 C 言語では文字はシングルクォーテーションマーク '' で囲みますが、これは コンピュータの内部処理では囲まれた文字のコードを示しています。 実は C 言語には文字と整数の明確な違いはありません。単に文字型は -128 から 127 までの値しか取れないだけです。 したがって、文字型の変数に対して、 printf 中で %d により表示すると、文 字コードを示す数字が表示されます。


#include <stdio.h>
main(){
  char x[]="abc";
  int i;
  for(i=0;x[i]!='\0';i++){
    printf("文字列 %s の %d 番目は %c で文字コードは %d\n",x,i,x[i],x[i]);
  }
}

C 言語では文字も整数とほぼ同様に扱いますので、加減乗除などの演算も可能 です。 さらに、文字コードで重要な性質として、現在のコンピュータではアルファベッ トの文字コードは連続しています (紙カードの時代の文字コードは違いました)。 そのため、例えば、'A'+1 は 'B' になります。 次のプログラムは実際正常に B を出力します。


#include <stdio.h>
main(){
  printf("%c",'A'+1);
}

従って、'A' と 'a' の文字コードを使うことで大文字小文字変換ができます。 例えば 'c' を大文字の'C' に変換することを考えます。 'c' から 'a' までの距離と 'C' から 'A' までの距離は等しいはずです。 つまり 'c'-'a'='C'-'A' となるはずです。これを移項すると 'c'-'a'+'A'='C' となります。従って入力が全て小文字の文字列を大文字にし て出力するには次のようにすれば良いです。


#include <stdio.h>
main(){
  char x[]="abc";
  int i;
  for(i=0;x[i]!='\0';i++){
    printf("%c",x[i]-'a'+'A');
  }
}

3-4. 演習

  1. char x[]="abc" と宣言されている時、この文字列の長さを出力するプロ グラムを書きなさい。
  2. char x[]="This is a pin." と宣言されている時、この文字列に含まれる i の数を出力するプログラムを書きなさい。
  3. char x[]="This is a pin." と宣言されている時、この文字列を全て大文 字で出力するプログラムを書きなさい (ヒント: 小文字だけを大文字にするようにします)。
  4. 二つの文字列 char x[]="abc", y[]="def" があり、 char z[50]; が宣言 されてたとします。この時、文字配列 z に文字列 x と y をつなげて一つの 文字列を作りなさい。
    
    #include <stdio.h>
    main(){
      char x[]="abc";
      char y[]="def";
      char z[50];
    
      /* 文字列をつなげる処理 */
      printf("文字列 %s と %s をつなげると %s になる\n",x,y,z);
    }
    

坂本直志 <[email protected]>
東京電機大学工学部情報通信工学科