-------------------------------------
#include<stdio.h>
int main(void)
{
int min,s,t,i,j;
int num[]={5,6,4,9,2};
for(i=0;i<4;i++){
min=num[i];
s=i; ////◎1
for(j=i+1;j<5;j++){
if(num[j]<min){
min=num[j];
s=j;
}
}
t=num[i];
num[i]=num[s];
num[s]=t;
}
for(i=0;i<5;i++){
printf("%d ",num[i]);
}
putchar('\n');
return 0;
}
--------------------------------------
以上のプログラムで◎1の記述が無くても正常にソートしてくれたので疑問に思いました。
「s=i;」が無い場合、最初のループのif文で、
if(num[j]<min){
min=num[j];
s=j;
}
「6<5」を比べる時、条件に見合わないので、sに何も代入されず、
t=num[i];
num[i]=num[s];
num[s]=t;
以上の記述で、sが初期化されてないので、その時点のエラーが出ると思ったんですが、出ないで正常に動きました。
何故なのか教えてもらえると嬉しいです。
No.4ベストアンサー
- 回答日時:
>以上の記述で、sが初期化されてないので、その時点のエラーが出ると思ったんですが、出ないで正常に動きました。
「◎1の行が無い場合に、sに値が一度も代入されず、不定になる」のは「元々、データがソート済みの時」だけです。
「元々、データがソート済みの時」と言うのは、言い換えれば
if(num[j]<min){
min=num[j];
s=j;
}
の部分を1度も通らない時、です。
◎1が存在する理由は「元々、データがソート済みの時、
if(num[j]<min){
min=num[j];
s=j;
}
の部分を1度も通らないから
t=num[i];
num[i]=num[s];
num[s]=t;
を行っても、入れ替えをしないようにする為」です。
最初に
s=i;
とやっておけば、元々ソート済みの場合
t=num[i];
num[i]=num[s];
num[s]=t;
の所に来た時にsとiが同じ値になっているので、入れ替えは起きません。
以下蛇足。
ANo.3の回答者さんへ
>☆コーディングでは、「インデント」すべきです。
当サイトでは、質問文中、回答文中の「行頭の半角スペース」は、自動的にすべてカットされてしまいます。
なので、質問者さんが「インデント済みの、ちゃんとしたコーディングをしたソースコード」を質問文に貼り付けても、すべてのインデントが勝手に削除されてしまいます。
従って、質問者さん(や他の回答者さん)に対して「ソースコードをインデントしてない」と言う指摘をするのは正当でない可能性があります。
「当サイトでは、インデントは勝手に消えてしまう」と言うのを念頭に置いて、今後、C/C++などのカテゴリで回答する際は「インデントすべき」と言う指摘はしない方が良いです。
下手に指摘すると「いちいちウルサイな。こっちはちゃんとインデントしてあるのを貼ってる。勝手にインデント消えるんだから仕方ないだろ」と思われてしまい、相手に悪い印象を与えます。ご注意を。
ご回答ありがとうございます。
>「◎1の行が無い場合に、sに値が一度も代入されず、不定になる」の>は「元々、データがソート済みの時」だけです。
if文の条件が1度も適合しないという事で、上記の内容理解できました。ありがとうございます。
No.5
- 回答日時:
No.3 です。
>2個目のfor文が範囲の分だけ繰り返し終わってから、
>t=num[i];
>num[i]=num[s];
>num[s]=t;
>以上に進むという感じですよね?
はい、そうです。
「 for 構文がどこまでか」が判った、ということですね。
(構文中で、break; を用い、ループ途中で抜け出すことも可能です)
>初心者なもので、すいません。
いえいえ、コーディングスタイル(インデント)云々より、「 for 構文の理解」でしたね。
後先となって、失礼しました。
今後は、コーディング時に適切にインデントしておけば、視覚的に把握できるかと・・。
No.4 さんへ
>当サイトでは、質問文中、回答文中の「行頭の半角スペース」は、自動的にすべてカットされてしまいます。
存じていました(このため No.3 回答文中では、全角空白を用いています)。
連続する複数の半角スペースが1つになること、タブも・・。
>下手に指摘すると「いちいちウルサイな。こっちはちゃんとインデントしてあるのを貼ってる。勝手にインデント消えるんだから仕方ないだろ」と思われてしまい、相手に悪い印象を与えます。ご注意を。
上手にアドバイスしたい、と思っているのですがなかなか・・、ご注意ありがとうございます。
最初からソートされていた場合、sに値が代入されず動作が不安定になるという事も理解していなかったのですが、ご指摘通りfor文が多重になった場合の事が、完全に理解できてなかったです。
その後勉強し理解できました。ありがとうございます。
No.3
- 回答日時:
>以上の記述で、s が初期化されてないので、その時点のエラーが出ると思ったんですが、出ないで正常に動きました。
いいえ、5より小さい4が現れた時点で、s に 2 が代入(「初期化」)されます。
そしてさらに、2で、s に 4 が代入されます。
最後の2まで比較してから、質問者様の言われる「その時点」に進みます。
先頭データが5でなく、1ですと質問者様期待どおりの結果となります(◆)。
+++++++++++++++++++++++++++++++++++++++++++++++
☆コーディングでは、「インデント」すべきです。
始めから下のようにコーディングしていたら、今回の質問はなかったのではないでしょうか。
for( i = 0; i < 4; i++ ){
min = num[ i ];
s = i; // このステップがない場合(◆)
for( j = ( i + 1 ); j < 5; j++ ){
if( num[ j ] < min ){
min = num[ j ];
s = j;
}
}
t = num[ i ];
num[ i ] = num[ s ]; // 「その時点」
num[ s ] = t;
}
ご回答ありがとうございます。
2個目のfor文が範囲の分だけ繰り返し終わってから、
t=num[i];
num[i]=num[s];
num[s]=t;
以上に進むという感じですよね?
確かに、先頭を「1」にすると、i=0の時、if文の条件が1度も適合せず実行は出来ましたが、エラーを報告する、しないの画面が出てしまいました。
初心者なもので、すいません。
No.2
- 回答日時:
>if(num[j]<min){
>min=num[j];
>s=j;
>}
上記の処理がfor文によるループの中に書いてあって、
1度だけ実行するわけではない(6<5の判定だけではない)ことに留意してください。
ご回答ありがとうございます。
まずi=0の時、
for(j=i+1;j<5;j++){
if(num[j]<min){
min=num[j];
s=j;
}
上記を4回繰り返してから、以下を1回実行するという感じですかね?
t=num[i];
num[i]=num[s];
num[s]=t;
初心者なもので、すいません。
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
似たような質問が見つかりました
- C言語・C++・C# 質問です 下記のコードを分かりやすく解説お願いします 初心者です #include ‹stdio.h 3 2022/05/26 22:03
- C言語・C++・C# C言語プログラム変更 2 2022/12/21 15:03
- C言語・C++・C# C言語でif文が予想と違う動きをする件について7 4 2023/03/20 00:26
- C言語・C++・C# c言語の問題の説明、各所ごとに 5 2023/07/26 11:03
- C言語・C++・C# C pointer? or... 2 2022/03/29 00:47
- C言語・C++・C# C++ と、 1 2022/11/07 23:45
- C言語・C++・C# C++プログラミングコードにポリモーフィズムを取り入れ方を教えてください。 2 2023/06/09 11:17
- JavaScript JAVASCRIPT 2 2022/04/15 15:10
- Excel(エクセル) VBA フォルダ見える化のコードについて 2 2023/06/19 15:04
- C言語・C++・C# C言語初心者 ポインタについて、お助けください、、 2 2023/03/15 23:50
関連するカテゴリからQ&Aを探す
おすすめ情報
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
配列を使って魔方陣
-
構文エラー";"が型の前にあり...
-
#if 1 #elseの意味について
-
for文の中にswitch文はいれられ...
-
C言語のプログラミング (基礎...
-
初心者です。for文、if文を使っ...
-
C言語 マスターマインドゲーム...
-
C言語プログラムが理解できなくて…
-
C言語 数字以外を入力させない...
-
C言語階乗の総和を求める
-
scanf関数を用いての加減乗除%...
-
while文について、c言語...
-
配列を関数に渡す方法
-
getcの改行判定
-
c言語for文
-
switch文とwhile文を用いたプロ...
-
scanfが実行されません
-
c言語についての質問です。
-
素因数分解のプログラムを作成...
-
C言語 入力した数値の平均値の...
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
#if 1 #elseの意味について
-
構文エラー";"が型の前にあり...
-
for文の中にswitch文はいれられ...
-
配列を関数に渡す方法
-
計算結果がlong型以上になる場...
-
プログラミングで二番目に大き...
-
scanf関数を用いての加減乗除%...
-
getcの改行判定
-
C言語で電卓を作成する。
-
配列を使って魔方陣
-
C言語で勉強中(max,min)の出し方
-
C言語階乗の総和を求める
-
VHDLで、case文とwhen文のどち...
-
C言語でのトランプシャッフルに...
-
プログラム
-
while文について、c言語...
-
OpenCVを用いて任意の時間で静...
-
scanfが実行されません
-
C言語 数字以外を入力させない...
-
C言語です
おすすめ情報