I.概要
前のセクションで、ソートはアルゴリズムの一部であると述べました。つまり、ソートはアルゴリズムの紹介でもあることを学びます。ソートがアルゴリズムの一部であるとみんなに感じさせるために、例を挙げてそれを証明します。たとえば、麻雀ゲームでは、カードが配られた後に対戦相手のカードをソートする必要があります。考えてみてください。麻雀ソートどうやって配置するの?その特徴は何ですか?そして、カードを引いたり、トランプをしたりする過程で、私たちは常にそれらを分類しなければなりません。どのソートアルゴリズムが最も速く選択できますか?
上記の状況では、どのソートアルゴリズムがより効率的かを分析できます。たとえば、次の画像にはすでに決まった順序でカードのセットがあります。
今度はカードを引く番です。引くカードは次のとおりです。
現時点で、この「同じカードの3つ」をカードの上段に配置するには、次のルールがあります。
1.通常の「3同一」は「2同一」と「4同一」の間に配置する必要があります。
2.他のスートのカードとは関係がなく、「5で」とも関係ありません。「2 with」と「4 with」の中間に「3 with」を置くだけです。「2 with」と「4 with」の位置は関係ありません。
選択ソートについて学習しましたが、上記のカードをソートするには選択ソートを使用するのが適切ですか?当然、選択順序を「70,000」から比較する必要があるため、最初のカードと位置を交換するために最小のカードが選択され、以下同様です。しかし、ここでは、麻雀牌の「同じ3つ」は「70,000」とは無関係であり、「70,000」に影響を与える必要はありません。したがって、時間の責任が大きいため、選択的並べ替えを使用することは適切ではありません。ここでは、挿入並べ替えを使用することをお勧めします。挿入並べ替えとは何ですか。これが、このセクションで紹介する必要があることです。
2、挿入ソート
挿入ソートは、単純なソートの一種であり、アルゴリズムが理解しやすいため、通常、単純なソートと呼ばれ、使い方が単純なわけではありません。誰もが挿入ソートをマスターできるようにするために、最初に挿入ソートの原理を見てみましょう。
2.1、挿入ソートの原理
まず、次のようにソートされる配列があります。
上記の配列には、配置する必要のある数値0が1つだけあり、他の数値は正しい順序になっています。この種類の配列は、挿入ソートを使用する方が効率的です。次に、この配列で挿入ソートを使用するプロセスについて説明します。
1.最初に1と2を比較します。2が1より小さい場合は、位置を入れ替えます。それ以外の場合、ポジションは交換されません。この配列は位置を交換する必要はありません。
2. 2と3をもう一度比較します。3が2より小さい場合は、位置を入れ替えます。ただし、実際の3は2より大きいため、位置は変更されず、変更されません。
3.同様に、3と4を比較するときに位置を切り替える必要はありません。
4.次に、4と0を比較します。0は4より小さいため、位置を入れ替えます
位置を交換した後の配列は次のとおりです。
5. 3の近傍が変更されたため、3と0が再度比較され、0は3より小さく、位置が交換されます。交換後の配列は次のとおりです。
6.同様に、0と2の位置を入れ替えた後の配列は次のようになります。
0と1のスワップ位置の配列は次のとおりです。
そのような配列の順序は正しいですが、ループはまだ完了していません。これは、番号4の位置にループしただけで、番号5は比較されていないためです。
7.最後に4と5を比較します。5が4より小さい場合、位置を入れ替えますが、5は4より大きいので、位置は変わりません。配列がループされた後、最終的なソートは次のようになります。
以上が挿入ソートの原理です。
2.2、挿入ソートと選択ソートの違い
たとえば、上記の例では、挿入ソートは0をインデックス4からインデックス3、2、1、0に移動し、最後に終了としてカウントします。選択ソートは、最小値0を見つけ、1と直接交換することです。位置は0から1、位置は1から0です。選択のソートについての前の紹介を読むことができます。
第三に、挿入ソートのコード実装
以下は、Javaコードの実装です。
/**
* 插入排序
*/
public static void algorithm5(){
//原始数组
int[] array={1,2,3,4,0,5};
//数组的长度
int length=array.length;
//对数组进行遍历
for (int i = 0; i < length; i++) {
//第二个循环仅仅是将当前数据跟自己左边的数字进行比较,如果小于左边数字则交换位置,否则位置不变。
for (int j = i; j > 0 && array[j]<array[j-1]; j--) {
int temp = 0;
temp = array[j-1];
array[j-1]=array[j];
array[j]=temp;
}
}
//将排好序的数组打印输出
for (int i = 0; i < length; i++) {
System.out.print(array[i]+",");
}
}
上記は、挿入ソートのJavaコード実装です。コードの2番目のforループは重要なポイントです。2番目のforループは、現在のデータの左側の値のみを比較します。左側の値よりも小さい場合、位置が交換されます。それ以外の場合、位置は変更されません。
3.1挿入ソートの時間の複雑さ
挿入ソートには、2種類の時間の複雑さがあります。
1.配列自体が{1、2、3、4、5}のように順序付けられている場合、挿入ソートを使用する時間の複雑さはO(n)です。理由:配列自体が順序付けられている場合、挿入ソートは2つおきの数値を隣り合わせに合計N-1回比較する必要があるため、時間の複雑度はO(n)です。
2.配列が順序付けられていない場合、最悪の場合(n ^ 2)/ 2回を比較する必要があるため、時間の複雑さはO(n ^ 2)です。
4、まとめ
挿入ソートの時間の複雑さによると、挿入ソートは次のタイプの配列に適しています。
1.配列の各要素が最終的な位置から遠くない。たとえば、{1,0,2,3,4,5}の場合、この配列の0の最終位置は最初の位置である必要があり、このときの0の位置は最初の位置から遠くないです。
2.小さい配列を順序付けられた大きい配列に組み込みます。たとえば、順序付けされた大きな配列{1,2,3,4,5,6}は、小さな配列{0,1}にマージされます。
3.配列内のいくつかの要素の位置のみが正しくありません。
上記の3種類の配列は、挿入ソートアルゴリズムに適しています。麻雀をした経験のある生徒は、麻雀をする過程で、カードを常に描いたり、遊んだり、並べ替えたりするプロセスは、1つの挿入だけではありません。
ソートはアルゴリズムの基礎であり、ソートには多くの用途があります。このセクションの内容を読んだ後、不要なカードをソートするコードを記述して、どのソートアルゴリズムがより適切であるかを確認することができます。