質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.50%
C

C言語は、1972年にAT&Tベル研究所の、デニス・リッチーが主体となって作成したプログラミング言語です。 B言語の後継言語として開発されたことからC言語と命名。そのため、表記法などはB言語やALGOLに近いとされています。 Cの拡張版であるC++言語とともに、現在世界中でもっとも普及されているプログラミング言語です。

Q&A

2回答

357閲覧

5つの英単語を入れ替える方法

shinto_0619

総合スコア6

C

C言語は、1972年にAT&Tベル研究所の、デニス・リッチーが主体となって作成したプログラミング言語です。 B言語の後継言語として開発されたことからC言語と命名。そのため、表記法などはB言語やALGOLに近いとされています。 Cの拡張版であるC++言語とともに、現在世界中でもっとも普及されているプログラミング言語です。

0グッド

0クリップ

投稿2019/08/03 18:24

前提・実現したいこと

与えられた関数を使って、5つ英単語を昇順、降順に並び替えるプログラムなんですがどれだけ考えてもわかりません助けてください

発生している問題・エラーメッセージ

該当のソースコード

c言語

試したこと

#include <stdio.h>
int cmp_str(char c1[], char c2[], int sort){
int flag=0,i;
for(int i=0; c1[i] != '\0' && c2[i] != '\0'; i++){
if(sort==1){
if(c1[i]>c2[i]){
flag=1;
break;
}
else if(c1[i]<c2[1]){
break;
}
}
else{
if(c1[i]<c2[i]){
flag=1;
break;
}
else if(c1[i]>c2[i]){
break;
}
}
}
if(sort==1 && c2[i]=='\0'){
flag=1;
}
else if(sort==2 && c1[i]=='\0'){
flag=1;
}
return flag;
}
int main(int argc, const char *argv[]){
int sort,i,j,flag,fga,fgb,fgc,fgd,fge;
char go[5][100],kotae[5][100];
fga=fgb=fgc=fgd=fge=0;
printf("昇順(1)or降順(2)?:");
scanf("%d",&sort);
printf("英単語を入力してください.\n");
for(i=0;i<5;i++){
scanf("%s",go[i]);
}
for(i=0;i<5;i++){
flag=cmp_str(go[i],go[i+1],sort);
if(flag==1){
fga=i;
}
if(flag==0){
fga=i+1;
}
}
for(i=0;i<5;i++){
if(fga==i){
continue;
}
flag=cmp_str(go[i],go[i+1],sort);
if(flag==1){
fgb=i;
}
if(flag==0){
if(fga==i+1){
continue;
}
fgb=i+1;
}
}
for(i=0;i<5;i++){
if(fga==i||fgb==i){
continue;
}
flag=cmp_str(go[i],go[i+1],sort);
if(flag==1){
fgc=i;
}
if(flag==0){
if(fga==i+1||fgb==i+1){
continue;
}

fgc=i+1; } } for(i=0;i<5;i++){ if(fga==i||fgb==i||fgc==i){ continue; } flag=cmp_str(go[i],go[i+1],sort); if(flag==1){ fgd=i; } if(flag==0){ if(fga==i+1||fgb==i+1||fgc==i+1){ continue; } fgd=i+1; } } for(i=0;i<5;i++){ if(fga==i||fgb==i||fgc==i||fgd==i){ continue; } flag=cmp_str(go[i],go[i+1],sort); if(flag==1){ fge=i; } if(flag==0){ if(fga==i+1||fgb==i+1||fgc==i+1||fgd==i+1){ continue; } fge=i+1; } } printf("%s\n %s\n %s\n %s\n %s\n",go[fga],go[fgb],go[fgc],go[fgd],go[fge]); return 0;

}
めちゃめちゃですが一応頑張ってみたつもりです。どうすれば良いでしょうか。

補足情報(FW/ツールのバージョンなど)

これが与えられた関数です

int cmp_str(char c1[], char c2[], int sort){
int flag=0,i;
for(int i=0; c1[i] != '\0' && c2[i] != '\0'; i++){
if(sort==1){
if(c1[i]>c2[i]){
flag=1;
break;
}
else if(c1[i]<c2[1]){
break;
}
}
else{
if(c1[i]<c2[i]){
flag=1;
break;
}
else if(c1[i]>c2[i]){
break;
}
}
}
if(sort==1 && c2[i]=='\0'){
flag=1;
}
else if(sort==2 && c1[i]=='\0'){
flag=1;
}
return flag;
}

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

takasima20

2019/08/03 23:14

各コードでなにをやりたいのかコメント追記されるとありがたいかなあ。
shiracamus

2019/12/04 16:06

ソースコードをcodeブロックで囲んでください。
guest

回答2

0

たとえば単純選択ソート

  1. go[0]~go[4]の中で最も小さい(大きい)go[x]を見つけ、go[0]と交換せよ。
  2. go[1]~go[4]の中で最も小さい(大きい)go[x]を見つけ、go[1]と交換せよ。
  3. go[2]~go[4]以下同文

つまり:

i = 0,1,..N-1 に対して:
go[i]~go[N-1]の中で最も小さい(大きい)go[x]を見つけ、go[i]と交換せよ。

C

1#include <stdio.h> 2 3int cmp_str(char c1[], char c2[], int sort) { 4 /* 実装は省略 */ 5} 6 7/* pとqを入れ換える */ 8void swap_str(char* p, char* q) { 9 /*------------------------- 10 * このナカミはあんたが埋めよ  11 *------------------------- */ 12} 13 14int main() { 15 int sort, i; 16 char go[5][100]; 17 18 printf("昇順(1)or降順(2)?:"); 19 scanf("%d",&sort); 20 printf("英単語を入力してください.\n"); 21 for(i=0;i<5;i++){ 22 scanf("%s",go[i]); 23 } 24 25 /* i = 0,1,..N-1 に対して: */ 26 for ( i = 0; i < 5; i++ ) { 27 /* go[i]~go[N-1]の中で最も小さい(大きい)go[x]を見つけ*/ 28 int x = i; 29 int j; 30 for ( j = i + 1; j < 5; ++j ) { 31 if ( cmp_str(go[inx],go[j],sort) ) { 32 x = j; 33 } 34 } 35 /* go[i] とgo[x] を交換せよ。*/ 36 swap_str(go[i], go[x]); 37 } 38 39 /* できたかな? */ 40 for ( i = 0; i < 5; ++i ) { 41 printf("%d: [%s]\n", i, go[i]); 42 } 43 return 0; 44}

投稿2019/08/03 22:06

編集2019/08/03 23:54
episteme

総合スコア16614

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

shinto_0619

2019/08/04 09:47

これでやってみたんですけど、Segmentation fault: 11と出てできませんでした。どこが違いますか? #include <stdio.h> int cmp_str(char c1[], char c2[], int sort){ int flag=0,i; for(int i=0; c1[i] != '\0' && c2[i] != '\0'; i++){ if(sort==1){ if(c1[i]>c2[i]){ flag=1; break; } else if(c1[i]<c2[1]){ break; } } else{ if(c1[i]<c2[i]){ flag=1; break; } else if(c1[i]>c2[i]){ break; } } } if(sort==1 && c2[i]=='\0'){ flag=1; } else if(sort==2 && c1[i]=='\0'){ flag=1; } return flag; } void swap_str(char p[],char q[]){ char temp; temp=*p; *p=*q; *q=temp; } int main(int argc, const char *argv[]){ int sort,i; char go[5][100]; printf("昇順(1)or降順(2)?:"); scanf("%d",&sort); printf("英単語を入力してください.\n"); for(i=0;i<5;i++){ scanf("%s",go[i]); } for(i=0;i<5;i++){ int x=i; int j; for(j=i+1;j<5;j++){ if(cmp_str(go[x],go[j],sort)){ x=j; } } swap_str(go[i],go[x]); } for(i=0;i<5;i++){ printf("%d: [%s]\n",i,go[i]); } return 0; }
episteme

2019/08/04 09:59 編集

swap_strがおかしいに決まってる。他にいぢるとこないし、僕のコードはちゃんと動いた。 swap_strは文字を入れ換えるのではない。文字「列」を入れ換えるのだ。
guest

0

もはや質問者は回答をアテにしてないんだろうけど、気になって調べて驚きました。提供されたという cmp_str() 関数がおかしいのです。関数仕様が明確ではありませんが推測は可能です。

C

1int cmp_str(char c1[], char c2[], int sort){ 2 int flag = 0, i; /// ここに i があるのに 3 4 /// for文の中にも i が・・・ 5 for(int i=0; c1[i] != '\0' && c2[i] != '\0'; i++){ 6 /// この中は省略 7 } 8 if(sort==1 && c2[i]=='\0'){ /// この i は不定値のまま 9 flag=1; 10 } 11 /// 以下も省略

これでは変数 i が2つ作られてしまいます。もちろんfor(int i = 0; の "int" は不要。明らかなバグです。セグメンテーションフォールトが起きたと質問者が言ったのは c2[i] のアクセスだと思います。

じゃ、int を消せば良いかというと、それでは済まないんです。こんなテストコードを書いてみました。

C

1struct { 2 char *s1; 3 char *s2; 4} sdata[] = { 5 { "abc", "abc" }, 6 { "abc", "abx" }, 7 { "abx", "abc" }, 8}; 9 10void test_cmp_str(void) 11{ 12 for (int i = 0; i < sizeof(sdata) / sizeof(sdata[0]); i++) { 13 char *a1 = sdata[i].s1; 14 char *a2 = sdata[i].s2; 15 16 printf("cmp_str(\"%s\", \"%s\", 1) => %d\n", 17 a1, a2, cmp_str(a1, a2, 1)); // 昇順? 18 printf("cmp_str(\"%s\", \"%s\", 2) => %d\n", 19 a1, a2, cmp_str(a1, a2, 2)); // 降順? 20 } 21}

わずか6ケース試しただけで早くもボロが出ました。

sh

1$ ./a.out 2cmp_str("abc", "abc", 1) => 0 3cmp_str("abc", "abc", 2) => 1 ←一致しても 1 を返す? 4cmp_str("abc", "abx", 1) => 0 5cmp_str("abc", "abx", 2) => 1 6cmp_str("abx", "abc", 1) => 0 ←え、0 を返すんですか? 7cmp_str("abx", "abc", 2) => 0

一致した時に1を返しても何とかなるかもしれないけど、"abx" と "abc" を比較したなら、どっちかは1を返さなきゃおかしいでしょ。

投稿する際に質問者が書き間違いしたのかもしれないが、最初からバグがあったというのが私の見立てです。なぜなら、私が気になったのは cmp_str() がダサいと見たからです。課題を出題する側のレベルがこうだとしたら、業界の将来(?)を心配しちゃいますね。
実際はどうだったのか、出題者は謝罪・訂正したのかw、質問者のコメントがほしいところです。

投稿2019/12/04 15:59

rubato6809

総合スコア1380

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.50%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問