
C言語標準入力でquitを入力で終わるプログラムを作っているのですが
うまくいきません
#include <stdio.h>
int main(void) {
int i, n;
double data[100];
printf("数字を入力してください。\n");
printf("入力を終えるときにはCtrl-dを押してください。\n");
n = 0;
while (scanf("%lf", &data[n]) != EOF) {
n++;
}
for (i=0; i<n; i++) {
printf("data[%d] = %f\n", i, data[i]);
}
return (0);
}
と今はとりあえづ作ってみたのですが
今のままではCtrl-dでループから抜ける形になっています
strcmp関数を使うとは思うのですが
strcmp関数はchar型なのでエラーが出てしまいます;
このやり方じゃないchar型にしてやり直さないといけないでしょうか;
Linux CentOS gcc
でやっています
標準入力で数字を入力しそれを格納
quitを入力するまで繰り返す
quitを入力で終了、これまで格納していた文字列の表示
簡単なプログラムの流れとしては上記の感じです
よろしくお願いします。
A 回答 (13件中1~10件)
- 最新から表示
- 回答順に表示
No.13
- 回答日時:
終了しますね。
>#12hogehog12345670000004quit
とか入力すると妙な挙動に見えるかも知れませんね。
標準入力に残る関係上しょうもないですかね。
まぁ、エラーケース考えるのは質問者さんに任せるとします。
# 勉強用だとエラー処理とか入っていなかったりとか多いですし。
# fgets()の戻り値もチェックしていなかったなぁ、そういえば…。
No.11
- 回答日時:
こんな感じですかねぇ……
インデントを全角空白でやっているのでコピペする場合はご注意を。
一応、CentOS6.5で動作確認はしましけど。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#define MCH 8
#define N 20
int main()
{
int data[N];
int nc = 0, i, flag;
char bff[MCH];
do
{
/* 入力 */
printf("data%d?:", (nc + 1));
fgets(bff,MCH,stdin);
/* "quit"だったら抜け */
if(strcmp(bff,"quit\n") == 0)
{
break;
}
/* 数字以外があるか確認 */
for(i = 0,flag = 1;bff[i] != '\n' && bff[i] != '\0';i++)
{
if(!isdigit(bff[i]))
{
flag = 0;
}
}
if(flag != 1)
{
printf("error:数字のみでお願いします。\n");
continue;
}
/* 5桁以上ならエラー(先のforループの結果、iは入力した文字数になっている) */
if(i > 5)
{
printf("error:5桁以内でお願いします。\n");
continue;
}
/* データ格納 */
if(i != 0)
{
data[nc++] = atoi(bff);
}
}while(nc < N);
/* 結果表示 */
printf("データ:\n");
for(i = 0;i < nc;i++)
{
printf("data[%d]=%d\n", i, data[i]);
}
return 0;
}
No.10
- 回答日時:
先は長そうですねぇ……
>:27: error: ‘else’ without a previous ‘if’
>else if(!isdigit(bff))
のelseに流れる為のif文はどれでしょう?
>:33: 警告: passing argument 1 of ‘strcpy’ makes pointer from integer without a cast …
>strcpy(a,bff);
char型に「文字列」は入れられません。
というか、この場合変数aに入っている謎の値がアドレスとして処理されます。(型が違うので怒られてますが)
>:35: 警告: passing argument 1 of ‘atoi’ makes pointer from integer without a cast …
>i=atoi(nc);
atoi()の引数はchar *かと。ncでは…アドレス0~10に数字が入っていることになります。
# 型がおかしいからやっぱり怒られる。
>:48: error: expected ‘while’ at end of input
久しぶりに「{」と「}」の対応が取れていません。
do {に対応する}は一番最後のものです。
よって、main()が閉じていませんので…
>:48: error: expected declaration or statement at end of input
こう言われます。
さて、他のツッコミ満載を消化しましょうかね。
>if(!(strcmp(bff,"quit\n")==0||nc==N))
ncがNだった時に…
>ch[nc++] = bff[0];
バッファオーバーフロー達成です。
ch[20]は安全に使える領域でしたか?
>char ch[N],a;
char型では値が入らない…と指摘済みですよね?
>scanf("%5d",bff);
%dで指定する場合は、結果を格納するアドレスを渡す必要があります。
bffはアドレスなのでまぁ、OKでしょう。
想定する動作はしませんが。
# bffからの連続する4バイトに「数値」が入ります。「数字」ではありませんのでご注意を。
# どう格納されるかは…エンディアン次第ですかね。(4バイトである保証もありませんが…まぁ、この場合どうでもいい話)
>else if(!isdigit(bff))
「isdigit()で1文字ずつ」と書いたかと思われますが……
何より引数の型が違うかと。(char *がintになったんですかねぇ…)
>printf("@ bff=%s",bff);
>printf("@ atoi(bff)=%d\n",atoi(bff));
入力のループの外にありますよ?
それで正しいのですか??
>fget(bff,MCH,stdin);
で数字を入力した場合は、まるっと捨てます。
# 後でscanf()しているから。
というかfgets()…ですよね??
なんというか、そろそろ回答例なコードでも乗せて強制終了した方がいいんじゃないか?
とか思い始めてきた……。
勉強にはたぶんならないけど。
すいません
長々付き合ってもらってしまって…
申し訳な過ぎるので
もお解答例を頂いて自分で勉強しようかと思ったのですが…
ご迷惑じゃなければ解答例を頂けないでしょうか
本当に長々付き合わせてすいませんでした
No.9
- 回答日時:
>→数値=コンピュータで計算できる数字
>数字=人間語でコンピュータで計算できない
>って言う認識なんですが…;
おおむね合っている…かなぁ。
念のため、「数値 数字」などでWeb検索してください。
>→条件:数字以外入力時はエラー表示し、再入力・全角数字の場合入力時はエラー表示し、再入力
>というのもあるので
エラー判定の追加があるようなので…
イメージとして掲示した中の
入力内容をコピー(ch[nc]=入力内容(数値で保持なら数字=>数値変換))
の前で、入力した文字列が数字のみかどうかの判定処理を追加してください。
http://linux.die.net/man/3/isdigit
のisdigit()で「1文字ずつ」判定していけばよいでしょう。
# 数字=>数値変換でエラーになったら…とかいう手もありますけどね。
# ただしatof()は使えないですが。sscanf()でもダメ…かなぁ…(先頭が数字だと…ね)
とりあえず
大まかな流れとしてはこんな感じですかね?
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#define MCH 8
#define N 20
int main(){
char ch[N],a;
int nc,quit,ic,b;
char bff[MCH];
printf("入力(quit by quit):\n");
nc=0;
do{
fget(bff,MCH,stdin);
if(!(strcmp(bff,"quit\n")==0||nc==N))
{
ch[nc++] = bff[0];
break;
}
else
{
scanf("%5d",bff);
printf("error:5桁以内でお願いします。\n");
}
else if(!isdigit(bff))
{
puts("error");
}
else
{
strcpy(a,bff);
ch[nc]=a;
i=atoi(nc);
}
while(!quit);
printf("@ bff=%s",bff);
printf("@ atoi(bff)=%d\n",atoi(bff));
printf("データ:\n");
for(ic=0;ic<nc;ic++)
{
b = ch[ic];
printf("ch[%d]=%d\n",ic,b);
/*printf("ch[%d] = %f\n",ic,ch[ic]);*/
}
return 0;
}
: In function ‘main’:
:27: error: ‘else’ without a previous ‘if’
:33: 警告: passing argument 1 of ‘strcpy’ makes pointer from integer without a cast
/usr/include/string.h:128: note: expected ‘char * __restrict__’ but argument is of type ‘char’
:35: 警告: passing argument 1 of ‘atoi’ makes pointer from integer without a cast
/usr/include/stdlib.h:148: note: expected ‘const char *’ but argument is of type ‘int’
:48: error: expected ‘while’ at end of input
:48: error: expected declaration or statement at end of input
めっちゃエラー出てしまったんですけどね…
これでも半分まで減らしましたが今出てるエラーは意味がわからなくて…
No.8
- 回答日時:
>ch[]の値はどこでどんな感じで入れたら良いですか?;
数値で入れたいのか、文字で入れたいのか…どちらです?
# とりあえず、「数値」と「数字」の区別はつきますか?
>charじゃないほうが良いということはdoubleとかにしないとってことですかね…?
数値…であれば、int型の配列でいいんじゃないですかね?
文字として…ということならばchar型の二次元配列なりになると思いますが。
>あと条件で
>5文字以上の場合入力時はエラー表示し、再入力
>というのがありまして
nc=0;
do{
fgets(bff,MCH,stdin);
bffがquitじゃないか判定。
=>quitだったらループ脱出フラグ設定
else
bffが5文字(5桁?)以内か判定
=>5文字以上ならエラーメッセージ表示
else
入力内容をコピー(ch[nc]=入力内容(数値で保持なら数字=>数値変換))
nc加算
ncが10か?
=>10だったらループ脱出フラグ設定
}while(!quit);
って感じですかね。
数字=>数値変換でエラーになる可能性もありますけど。
「"wktk"を数値にせよ。」とか言われても困るでしょう?
# とりあえず、「数値」と「数字」の区別はつきますか?
→数値=コンピュータで計算できる数字
数字=人間語でコンピュータで計算できない
って言う認識なんですが…;
数値…であれば、int型の配列でいいんじゃないですかね?
文字として…ということならばchar型の二次元配列なりになると思いますが。
→条件:数字以外入力時はエラー表示し、再入力・全角数字の場合入力時はエラー表示し、再入力
というのもあるので
intですかね;
nc=0;
do{
fgets(bff,MCH,stdin);
bffがquitじゃないか判定。
=>quitだったらループ脱出フラグ設定
else
bffが5文字(5桁?)以内か判定
=>5文字以上ならエラーメッセージ表示
else
入力内容をコピー(ch[nc]=入力内容(数値で保持なら数字=>数値変換))
nc加算
ncが10か?
=>10だったらループ脱出フラグ設定
}while(!quit);
って感じですかね。
→ありがとうございます。ちょっとそのやり方でやってみますね;
No.7
- 回答日時:
>データ:
>ch[0] = ?
>ch[1] = A
>となって値が出てこなかったです;
出てきたら恐怖です。
>do{
>fgets(bff,MCH,stdin);
>if(!(quit=strcmp(bff,"quit\n")==0||nc==N)){
>nc++;
>}
>}
>while(!quit);
のどこで、ch[]に値を入れているのでしょうか?
あと…ch[]はchar型なので、入力した内容を数値として持つつもりなら
>234
>345
234はともかく345は入りません。(char型には255まで…でしょう。signed charだったら127)
さらに…
>printf("ch[%d] = %c\n",ic,ch[ic]);
%cで出力すると入力値によっては画面壊れたりしますよ。
# 表示できない文字コードだった…とか、コントロールコードだった…とか……。
ch[]の値はどこでどんな感じで入れたら良いですか?;
あと条件で
5文字以上の場合入力時はエラー表示し、再入力
というのがありまして…記載するのを忘れていましたが…
charじゃないほうが良いということはdoubleとかにしないとってことですかね…?
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#define MCH 8
#define N 20
int main(){
char ch[N];
int nc,quit,ic,b;
char bff[MCH];
printf("入力(quit by quit):\n");
nc=0;
do{
fgets(bff,MCH,stdin);
if(!(quit=strcmp(bff,"quit\n")==0||nc==N)){
ch[nc++] = bff[0];
}
}while(!quit);
printf("@ bff=%s",bff);
printf("@ atoi(bff)=%d\n",atoi(bff));
printf("データ:\n");
for(ic=0;ic<nc;ic++)
{
b = ch[ic];
printf("ch[%d]=%d\n",ic,b);
/*printf("ch[%d] = %f\n",ic,ch[ic]);*/
}
return 0;
}
No.6
- 回答日時:
指摘漏れ。
>printf("str[%s] = %s\n",i,str[i]);
最初の%sで、アドレス0からの文字列を表示。
gccってことだからたぶん"(null)"で済むでしょう。
が、その次の%sで…str[0]の値がアドレスとして使用されて…ここでもセグメンテーションフォルト発動…でしょうね。
>char str[10];
では、入力された情報を保持し続けるには足りません。
>while(scanf("%s",str[n])){
>if(!(quit=strcmp(str,"quit\n") == 0 || n == 10))
でnが10になっていた時には手遅れです。
配列の添え字の範囲について再度勉強し直してください。
# char str[10];
# で確保された配列は…
# str[0]~str[10]まで使えますか?
# str[1]~str[10]でしったけ?
指摘と自分なりに考えて下記のようにしてみました。
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#define MCH 8
#define N 20
int main(){
char ch[N];
int nc,quit,ic;
char bff[MCH];
printf("入力(quit by quit):\n");
nc=0;
do{
fgets(bff,MCH,stdin);
if(!(quit=strcmp(bff,"quit\n")==0||nc==N)){
nc++;
}
}
while(!quit);
printf("データ:\n");
for(ic=0;ic<nc;ic++)
{
printf("ch[%d] = %c\n",ic,ch[ic]);
}
return 0;
}
gccでコンパイラ時のエラーはありませんでした
実行
入力(quit by quit):
234
345
quit
データ:
ch[0] = ?
ch[1] = A
となって値が出てこなかったです;
No.5
- 回答日時:
>error: expected declaration or statement at end of input
14行目と16行目が対。(問題なし)
18行目と22行目が対。(だけど途中のreturnで終了)
5行目のmain()開始の「{」と、12行目のwhile()ループ開始の「{」が片思い中です。
あと……
>char str[10];
>scanf("%s",str[n])
入力された文字列を、どっか判らないアドレス(str[]は未初期化の変数なので入っている値は不定)に入れてね♪
ということで、コンパイルエラーを修正しても実行して入力した段階でセグメンテーションフォルトの魔法が発動でプロセス殺人事件が発生します。
犯人は……OSだっ!!
# 真犯人は仕組んだプログラマーだ。
No.4
- 回答日時:
>passing argument 1 of 'strcmp' from incompatible pointer type
strとした時とstr[n]とした時で型が異なりますが、その辺りは理解してます?
>while(scanf("%s",str[n]));
>if(!(quit=strcmp(str,"quit\n") == 0 || n == 10))
scanf()で入力を受け取ったのはstr[n][0]からstr[n][9]の範囲。
strcmp()で比較したいのはどこですか?
# あと、scanf()で受け取った時に改行文字入っていますか??
>error: expected 'while' at end of input
while()の後にセミコロンありますが、正しいですか?
というか、12行目にあるdoに対応するwhile()ってどれです?
>error: expected declaration or statement at end of input
「{」と「}」の対応が取れていません。
main()の「{」(5行目)に対応する「}」がありません。
vimでも対応する括弧は色を変えて表示してくれるオプションがあったと思いますのでその辺り確認しましょう。
ちなみに、16行目と18行目が対、
20行目と22行目が対、
13行目と24行目が対になっています。
# 24行目の対がmain()の開始…なのでしょうから、13行目の対が無い(というかdoに対応するwhile()が不明)というのが問題なのでしょう。
すいません;
少し直してみました;;;
#include <stdio.h>
#include <string.h>
int main(void)
{
int i,n,quit;
char str[10];
printf("プログラムを終了するにはquitを入力してください\n");
n = 0;
while(scanf("%s",str[n])){
if(!(quit=strcmp(str,"quit\n") == 0 || n == 10))
{
n++;
}
for(i=0;i<n;i++)
{
printf("str[%s] = %s\n",i,str[i]);
return 0;
}
gcc後のエラー↓
#ファイル名: In function 'main'*
#ファイル名#:22: error: expected declaration or statement at end of input
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
似たような質問が見つかりました
- C言語・C++・C# 10個の実数に対する降順ソート結果を出力するプログラムを作りたいのですが、以下のプログラムをどう直せ 1 2022/07/09 22:16
- C言語・C++・C# c言語配列の結合についてです。 なぜうまくいかないのでしょうか。 #include <stdio.h 4 2022/05/30 22:42
- C言語・C++・C# c言語の問題です 3 2023/01/10 16:15
- C言語・C++・C# c言語でユーザ関数を利用して入力された文字列を反転させるプログラムを作りたいです。 3 2023/01/29 19:47
- C言語・C++・C# C言語 3 2022/10/04 15:07
- C言語・C++・C# C言語(構造体) 3 2022/07/05 20:08
- C言語・C++・C# C言語のエラーについて 2 2022/07/11 13:56
- C言語・C++・C# 至急教えてください!プログラミングの問題です。 割られる整数と割る整数を受け取って、商と余りを出力す 3 2022/07/05 10:23
- C言語・C++・C# プログラミングの授業の課題です 1 2023/01/17 22:15
- C言語・C++・C# 至急教えてください。プログラミングの問題です。 最初に正の整数nの入力を受け付け、次に分数の分子と分 1 2022/07/19 17:03
関連するカテゴリからQ&Aを探す
おすすめ情報
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
プログラミングについて。 1つ...
-
gccを行ってもexeファイルが生...
-
c言語
-
visual studio 2022でのC#プロ...
-
C# DatagridviewにExcelシート...
-
mallocについて
-
C言語って古いですか?
-
C言語関数違いについて。
-
逆コンパイルと逆アセンブルの...
-
プログラムの実行時に'<'でリダ...
-
パソコン
-
CPUが16bitでも32bitOSでコンパ...
-
Python、プログラミングについ...
-
だれがとけるの?
-
バッチファイルで以下のような...
-
Notepad++の関数リスト表示の変...
-
VisualStudio2022でC言語プログ...
-
License='MIT' ってなんでmitな...
-
C言語 ストリームについて。
-
c言語でイベントフラグを使った...
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
c言語
-
gccを行ってもexeファイルが生...
-
大量のデータを読み込んで表示...
-
visual studio 2022でのC#プロ...
-
C++でデスクトップGUIアプリ開...
-
【C言語】全角文字の配列を、全...
-
Windows Formアプリからコンソ...
-
VisualStudio2022でC言語プログ...
-
C#でログファイルにファイルパ...
-
C#でTreeViewのCheckBoxのサイ...
-
c#のTLS1.2での通信について
-
VisualStudioでC++クラスを追加...
-
C言語について。
-
int16_t の _t は何?
-
プログラマー達は何故、プログ...
-
逆コンパイルと逆アセンブルの...
-
C言語の関数のextern宣言
-
c言語でイベントフラグを使った...
-
C言語 関数、変数の宣言について
-
[C言語]fputsとfprintfの違い
おすすめ情報