Javaで単一の文字列をソートする


131

文字列をJavaの内容で並べ替えるネイティブな方法はありますか?例えば

String s = "edcba"  ->  "abcde"

回答:


215

toCharArray続いArrays.sortて文字列コンストラクター呼び出しが続きます:

import java.util.Arrays;

public class Test
{
    public static void main(String[] args)
    {
        String original = "edcba";
        char[] chars = original.toCharArray();
        Arrays.sort(chars);
        String sorted = new String(chars);
        System.out.println(sorted);
    }
}

編集:タックラインが指摘するように、文字列にサロゲートペアまたは実際に複合文字(アクセント+ eが別々の文字として含まれる)などが含まれている場合、これは失敗します。さらに、これは、大文字、アクセントなどを考慮せずに、序数で並べるだけです。


2
正しい方法は、コードポイントを並べ替えることです。残念ながら、String.toCodePointArrayはありません。(ところで、私たちはどのような順序でソートすべきですか?)
トム・ホーティン-タックライン

1
ICUプロジェクトは、コードポイントオーダーUTF-16ソートメソッドを記述しています:icu-project.org/docs/papers/utf16_code_point_order.html。範囲の定義方法が原因でArrays.sortが補助文字を破棄することはないと思いますが、引用しないでください。
McDowell

1
おそらく何も破壊されませんが、大文字やアクセントなどを考慮したい場合、ソート順は最適ではありません。このアルゴリズムは「éDedCBcbAàa」を「ABCDabcdeàé」としてソートしますが、たとえば英語(US)ロケールでは、「aAàbBcCdDeé」を取得する方が望ましいでしょう。
eljenso

1
@YiweiGそしてこの場合、答えは次のとおりです。sortedすでにStringです...あなたはtoString()それに何を要求することを期待しますか?
Jon Skeet、2014

1
@ヘンゲーム:文字配列を並べ替えていますが、無視しています。あなたがしたいchar[] c = s.toCharArray(); Arrays.sort(c); String sorted = new String(c);
ジョン・スキート

49

いいえ、組み込みのStringメソッドはありません。これをchar配列に変換し、Arrays.sortを使用してソートし、それをStringに戻すことができます。

String test= "edcba";
char[] ar = test.toCharArray();
Arrays.sort(ar);
String sorted = String.valueOf(ar);

または、大文字やアクセント付き文字などのロケール固有のものを正しく処理したい場合:

import java.text.Collator;
import java.util.Arrays;
import java.util.Comparator;
import java.util.Locale;

public class Test
{
  public static void main(String[] args)
  {
    Collator collator = Collator.getInstance(new Locale("fr", "FR"));
    String original = "éDedCBcbAàa";
    String[] split = original.split("");
    Arrays.sort(split, collator);
    String sorted = "";
    for (int i = 0; i < split.length; i++)
    {
      sorted += split[i];
    }
    System.out.println(sorted); // "aAàbBcCdDeé"
  }
}

参考:このメソッドは、32ビットコードポイントを2つに分割します-値が0xFFFFより大きいUnicode文字で、無効な値の文字列を作成します。フランス語では問題ありませんが、ロケールによっては問題が発生する可能性があります。
McDowell

Character.isHighSurrogate(char)を参照してください
マクダウェル

1
どういうわけか私はこれがうまくいくと思います...彼がスワヒリ語または何かを含む文字

3
「これでうまくいくと思います...スワヒリ語を含む文字列をソートしたくない場合」-スローガンを見ることができます-Unicode:アプリケーションをいくつかの言語にローカライズおよび翻訳する簡単な方法が必要な場合。Bzzt。不合格。こう事はほとんど右手段は、あなたは、ほぼ後で修正するバグを持っていません。
JonasKölker

@ジョナス私は、OPがスワヒリ語をサポートすることが絶対に必要であると指定したくない限り、私は思いました。OPで十分ではないと述べられていない限り、私はロケールなしの単純なソリューションを好むことさえあります。YAGNIの原則を聞いたことがありますか?
eljenso

32

Java 8では、次の方法で実行できます。

String s = "edcba".chars()
    .sorted()
    .collect(StringBuilder::new, StringBuilder::appendCodePoint, StringBuilder::append)
    .toString();

長さが1の文字列のストリームで機能する少し短い代替(ソートされていない文字列の各文字は、ストリームの文字列に変換されます)は次のとおりです。

String sorted =
    Stream.of("edcba".split(""))
        .sorted()
        .collect(Collectors.joining());

@Dennis正確に、そしてなぜですか?
Marcin

文字列をソートしようとする最初のビット。見た目は良いですが、大規模なデータセットに対して実行した場合、Jon Skeetsの回答と比較するとかなり低速でした。
Dennis

18

文字の配列に変換ソート文字列に変換

String s = "edcba";
char[] c = s.toCharArray();        // convert to array of chars 
java.util.Arrays.sort(c);          // sort
String newString = new String(c);  // convert back to String
System.out.println(newString);     // "abcde"

他の人々が少なくとも3つの同一の回答を投稿してから4年後にこの回答を追加したことの意味は何でしたか
Nick Cardoso

1
@NickCardoso私は本当に覚えていません。StackOverflowの非常に早い段階で投稿した回答について質問されています。あなたはそれについての説明を本当に待っていますか?
Maroun

@NickCardoso私はあなたに言い訳をするつもりは全くありません。あなたのコメントと反対投票は、今のところ何も変更しません。それが4年前に私が決めたものです、今これを持ち出すことの意味が何であるかわかりません:)
Maroun

16

sort Arrays.sortメソッドを使用しない、より生のアプローチ。これは挿入ソートを使用しています。

public static void main(String[] args){
    String wordSt="watch";
    char[] word=wordSt.toCharArray();

    for(int i=0;i<(word.length-1);i++){
        for(int j=i+1;j>0;j--){
            if(word[j]<word[j-1]){
                char temp=word[j-1];
                word[j-1]=word[j];
                word[j]=temp;
            }
        }
    }
    wordSt=String.valueOf(word);
    System.out.println(wordSt);
}

1
他の並べ替えアルゴリズムを使用せずに、Javaでのネイティブな方法を尋ねる質問。
Vikrant Goel 2013年

1
それが有用な解決策であったためではなく、要求された回答だったためではありませんでした。
Chris

1
@VikrantGoel "Javaのネイティブな方法"-このアプローチのネイティブではないものは何ですか?サードパーティの要件はありません。あなたは?
Nick Cardoso

これが正解です。@NickCardosoが言ったように...これ以上「Javaのネイティブな方法」はありません。
マリアーノゾリラ

14
    String a ="dgfa";
    char [] c = a.toCharArray();
    Arrays.sort(c);
    return new String(c);

大文字と小文字が混在する文字列の場合、これは期待どおりに機能しないことに注意してください(大文字の前に小文字が追加されます)。コンパレータをSortメソッドに渡して、それを変更できます。


1
java.util.Arraysをインポートする必要があります。それ以外の場合は機能しません
ホッパー

3

手順:

  1. 最初に文字列をchar配列に変換します
  2. 次に、文字の配列を並べ替えます
  3. 文字配列を文字列に変換します
  4. 文字列を印刷する

コードスニペット:

    String input = "world";
    char[] arr = input.toCharArray();
    Arrays.sort(arr);
    String sorted = new String(arr);
    System.out.println(sorted);

これは冗談ですか?8歳の質問に同じ回答を投稿しますか?なんて怠惰なんだ。
Nick Cardoso

私は無知です。私を許して。
rashedcs

2

質問:Javaで文字列を並べ替える

public class SortAStringInJava {
    public static void main(String[] args) {

        String str = "Protijayi";
// Method 1
        str = str.chars() // IntStream
                .sorted().collect(StringBuilder::new, StringBuilder::appendCodePoint, StringBuilder::append).toString();

        System.out.println(str);
        // Method 2
        str = Stream.of(str.split(" ")).sorted().collect(Collectors.joining());
        System.out.println(str);
    }
}

-1
public static void main(String[] args) {
    String str = "helloword";   
    char[] arr;
    List<Character> l = new ArrayList<Character>();
    for (int i = 0; i < str.length(); i++) {
        arr = str.toCharArray();
        l.add(arr[i]);

    }
    Collections.sort(l);
    str = l.toString();
    System.out.println(str);
    str = str.replaceAll("\\[", "").replaceAll("\\]", "")
            .replaceAll("[,]", "");
    System.out.println(str);

}

-2

Javaでコレクションを使用しない場合:

import java.util.Scanner;

public class SortingaString {
    public static String Sort(String s1)
    {
        char ch[]=s1.toCharArray();         
        String res=" ";
        
        for(int i=0; i<ch.length ; i++)
        {
            for(int j=i+1;j<ch.length; j++)
            {
                if(ch[i]>=ch[j])
                {
                    char m=ch[i];
                    ch[i]=ch[j];
                    ch[j]=m;
                }
            }
            
            res=res+ch[i];
            
        }

        return res;
    }

    public static void main(String[] args) {
        Scanner sc=new Scanner(System.in);
        System.out.println("enter the string");
        
        String s1=sc.next();
        String ans=Sort( s1);
        
        System.out.println("after sorting=="+ans);
    }
}

出力:

文字列を入力してください==

仕分け

ソート後==ギノスト


> =をもう一度見てください。文字列として「mnmnmnm」を使用するとどうなりますか?
Nick Cardoso
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.