入力された文字列を英字、数字、その他で分けて表示するプログラム

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
アバター
kerotan0820
記事: 91
登録日時: 9年前
住所: 東京都
連絡を取る:

入力された文字列を英字、数字、その他で分けて表示するプログラム

#1

投稿記事 by kerotan0820 » 8年前

「入力された文字列を、英字、数字、その他に分けて出力せよ」

このような問題が学校で出題されました。

学校の先生に質問してみたところ、原因はわからないからやらなくていいと言われてしまったのですが、納得もいかないので質問をさせていただきました。

プログラムは此方です。

コード:

#include<stdio.h>
#include <string.h>

int main(void)
{
	char str[50],Emoji[50],Nmoji[50],Elsemoji[50];
	char *x;
	int i=0,j=0,k=0,h=0,len=0;


	scanf(" %s",str);							//入力された文字列を保存
	x = str;
	
	while( *x != '\0')							//終端文字出ない限りループ
	{
		if(*x >= 65 || *x <= 122)				//英文字ならば
		{
			Emoji[i] = *x;						//英文字用配列に格納
			i++;
		}
		
		if( *x >= 48 || *x <= 57)				//数字ならば
		{
			Nmoji[j] = *x;						//数文字用配列に格納
			j++;
		}

		else									//英語、数字以外の場合
		{
			Elsemoji[k] = *x;					//Else配列に格納
			k++;
		}
		x++;
	}

	printf("英文字は:%s \n",Emoji);
	printf("数文字は:%s \n",Nmoji);
	printf("それ以外:%s \n",Elsemoji);

	return 0;
}
① 文字列を入力し配列 str に格納する。
② ポインタ変数 x に str の先頭アドレスを渡す
③ x の指す実態が、終端文字 ¥0 出ない限り while文を回す
④ while文では、文字が英字、数字、その他のどれなのかを識別し任意の配列に仕分けしていく。
⑤ 仕分けされた英字、数字、その他の3種の配列の中身を表示する。

ちなみに、isdigit などの文字の要素を調べる関数は使わないつもりで考えています。
(この課題のあとに関数の説明があったため、使わない前提での問題だと思います) 

01ab と入力してみたところこのような結果になりました。
無題.png
無題.png (50.99 KiB) 閲覧数: 4550 回
全ての条件分岐を満たしてどれもに 01ab という文字が入ってしまっているように見受けられます。
フフフフフ という文字は何が原因なのか全くわかりません。

しばらく調べたり、プログラムを分割して動作させてみたりしたのですが、結局何処が原因になっているのかわかりませんでした。

大変お手数をお掛けしますが、ご教示頂けませんでしょうか。
[hr]
追記:
無題.png
無題.png (49.24 KiB) 閲覧数: 4545 回
10進数で表示される値で比較していることは間違いではないはずですし、何がいけないのかやはりよくわかりません...
けろけろにゃー (」・ω・)」うー!

アバター
へにっくす
記事: 630
登録日時: 8年前
住所: 東京都

Re: 入力された文字列を英字、数字、その他で分けて表示するプログラム

#2

投稿記事 by へにっくす » 8年前

C/C++言語で言う文字列とは何か?
終端文字で終わる文字の配列。
この、終端文字というのが掲示されているソースでは代入されてませんよね。
だから結果としては当然です。
C/C++言語では初期化していないと何が入っているか分からないのです。
(コンパイルオプションで0で初期化するものもあるけど、全てのコンパイラにあるわけではありません)

これを回避するには、変数を0で初期化するか、
文字を入れた後、その次の位置に0を代入(=終端文字を代入)するかです。

コード:

char str[50]={0}; // 全部0にする
char str2[50];
str[0]='a';
str2[0]='a';
str2[1]='\0'; // 文字列の最後は必ず終端文字
printf("str=%s,str2=%s", str, str2); // 両方とも a と表示されるはず
また文字の判定がおかしい?
たとえば数字の判定なら以下のようになるはずでは?

コード:

if( (*x >= 48) && (*x <= 57) ) // if( (*x >= '0') && (*x <= '9') ) の方が分かりやすいと思うが…
if … のあとに if … else … となってるのも変だよね。
if … else if … else … とすべきです。
written by へにっくす

アバター
kerotan0820
記事: 91
登録日時: 9年前
住所: 東京都
連絡を取る:

Re: 入力された文字列を英字、数字、その他で分けて表示するプログラム

#3

投稿記事 by kerotan0820 » 8年前

へにっくす さんが書きました: Re: 入力された文字列を英字、数字、その他で分けて表示するプログラム
解答有難うございます。

オアになっていたの、気づきませんでした。ありがとうございます。 アンドになおしておきました。


終端文字は自動でつくものだと勘違いしておりました…。

入力された文字の長さを取得し、その数+1のところに終端文字を入れるようにプログラムを書き換えたのですが、正常に動きませせん。

コード:

	scanf(" %s",str);							//入力された文字列を保存
	x = str;

	len = strlen(str);
	str[len+1] = '\0';
けろけろにゃー (」・ω・)」うー!

アバター
へにっくす
記事: 630
登録日時: 8年前
住所: 東京都

Re: 入力された文字列を英字、数字、その他で分けて表示するプログラム

#4

投稿記事 by へにっくす » 8年前

kerotan0820 さんが書きました:入力された文字の長さを取得し、その数+1のところに終端文字を入れるようにプログラムを書き換えたのですが、正常に動きませせん。
そりゃそうでしょ。入力された文字列に入れてどうすんねん。
printfに渡している変数は何だ?
それに対して終端文字を入れなきゃ。
whileを抜けた後は、i, j, kそれぞれが終端文字を書く位置になってるよ。
written by へにっくす

アバター
kerotan0820
記事: 91
登録日時: 9年前
住所: 東京都
連絡を取る:

Re: 入力された文字列を英字、数字、その他で分けて表示するプログラム

#5

投稿記事 by kerotan0820 » 8年前

へにっくす さんが書きました:
kerotan0820 さんが書きました:入力された文字の長さを取得し、その数+1のところに終端文字を入れるようにプログラムを書き換えたのですが、正常に動きませせん。
そりゃそうでしょ。入力された文字列に入れてどうすんねん。
printfに渡している変数は何だ?
それに対して終端文字を入れなきゃ。
whileを抜けた後は、i, j, kそれぞれが終端文字を書く位置になってるよ。
scanfで入力を求めたものにも、終端文字を自分で入れないといけないのかと思ってしまいました…。
確かに printf で表示する配列は、最初カラの状態で一文字づつ代入していったので終端文字が自動で付くわけもないですね。

当たり前のことに気づけなくてすみません。

それと、else の処理が数字以外の場合全て代入されてしまうということにも気づきました。
情けない。

ありがとうございました。
けろけろにゃー (」・ω・)」うー!

閉鎖

“C言語何でも質問掲示板” へ戻る