Sắp xếp một chuỗi trong Java


131

Có cách nào để sắp xếp Chuỗi theo nội dung của nó trong java không? Ví dụ

String s = "edcba"  ->  "abcde"

Câu trả lời:


215

toCharArraytheo sau Arrays.sortlà một lệnh gọi hàm tạo chuỗi:

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);
    }
}

EDIT: Như tackline chỉ ra, điều này sẽ thất bại nếu chuỗi chứa các cặp thay thế hoặc các ký tự hỗn hợp thực sự (dấu + e là các ký tự riêng biệt), v.v. Tại thời điểm đó, nó sẽ khó hơn rất nhiều ... hy vọng bạn không cần điều này :) Ngoài ra, đây chỉ là thứ tự theo thứ tự, mà không cần viết hoa, dấu hoặc bất cứ điều gì khác vào tài khoản.


2
Cách chính xác sẽ là sắp xếp các điểm mã. Thật không may, không có String.toCodePointArray. (Chúng ta nên sắp xếp theo thứ tự nào, btw?)
Tom Hawtin - tackline

1
Dự án ICU mô tả một phương pháp sắp xếp UTF-16 theo thứ tự điểm mã: icu-project.org/docs/ con / utf16_code_point_order.html . Tôi không nghĩ Arrays.sort sẽ phá hủy bất kỳ ký tự bổ sung nào do cách xác định phạm vi, nhưng đừng trích dẫn tôi.
McDowell

1
Nó có thể sẽ không phá hủy bất cứ thứ gì, nhưng thứ tự sắp xếp không tối ưu nếu bạn muốn tính đến chữ hoa và dấu trọng âm chẳng hạn. Thuật toán này sẽ sắp xếp "éDedCBcbAàa" thành "ABCDabcdeàé" trong khi, bằng tiếng Anh (Hoa Kỳ) chẳng hạn, sẽ mong muốn có được "aAàbBcCdDeé".
eljenso

1
@YiweiG Và trong trường hợp này, câu trả lời là: chắc chắn là không. sortedđã là một String... bạn muốn gọi toString()nó để làm gì?
Jon Skeet

1
@Hengameh: Bạn đang sắp xếp một mảng ký tự, nhưng sau đó bỏ qua nó. Bạn muốnchar[] c = s.toCharArray(); Arrays.sort(c); String sorted = new String(c);
Jon Skeet

49

Không có không có phương thức String tích hợp. Bạn có thể chuyển đổi nó thành một mảng char, sắp xếp nó bằng Arrays.sort và chuyển đổi nó trở lại thành Chuỗi.

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

Hoặc, khi bạn muốn xử lý chính xác các nội dung cụ thể của miền địa phương như chữ hoa và ký tự có dấu:

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é"
  }
}

FYI: phương pháp này sẽ chia các điểm mã 32 bit thành hai - ký tự Unicode có giá trị lớn hơn 0xFFFF, tạo các chuỗi có giá trị không hợp lệ. Không phải là một vấn đề cho tiếng Pháp, nhưng có thể gây ra vấn đề cho một số địa phương.
McDowell

Xem Character.isHighSurrogate (char)
McDowell

1
Bằng cách nào đó tôi nghĩ rằng điều này sẽ làm ... trừ khi anh ta muốn sắp xếp các chuỗi có chứa tiếng Swords hoặc thứ gì đó :)
eljenso

3
"Tôi nghĩ rằng điều này sẽ làm ... trừ khi anh ấy muốn sắp xếp Chuỗi có chứa tiếng Swiêng" - Tôi có thể thấy khẩu hiệu - Unicode: khi bạn muốn một cách dễ dàng bản địa hóa và dịch các ứng dụng của mình sang một số ngôn ngữ. Bzzt. Thất bại. Làm điều gần như đúng có nghĩa là bạn gần như không có lỗi để sửa sau này.
Jonas Kölker

@ Tôi nói tôi nghĩ , trừ khi OP muốn xác định rằng nó hoàn toàn cần thiết để hỗ trợ tiếng Swiêng. Tôi thậm chí thích giải pháp đơn giản mà không cần miền địa phương, trừ khi OP tuyên bố rằng nó không đủ. Bạn đã từng nghe về nguyên tắc YAGNI chưa?
eljenso

32

Trong Java 8, nó có thể được thực hiện với:

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

Một thay thế ngắn hơn một chút hoạt động với Luồng chuỗi có độ dài một (mỗi ký tự trong Chuỗi chưa được sắp xếp được chuyển đổi thành Chuỗi trong Luồng) là:

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

@Dennis trên cái nào chính xác và tại sao?
Marcin

Bit đầu tiên nơi bạn cố gắng sắp xếp một Chuỗi. Nó có vẻ tốt nhưng khi tôi chạy nó với một tập dữ liệu lớn thì nó chậm hơn một chút so với câu trả lời của Jon Skeets.
Dennis

18

Chuyển đổi thành mảng ký tựSắp xếpChuyển đổi trở lại Chuỗi :

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"

Điểm quan trọng trong việc thêm câu trả lời này 4 năm sau khi người khác đăng ít nhất 3 câu trả lời giống hệt nhau
Nick Cardoso

1
@NickCardoso Tôi thực sự không nhớ, bạn đang hỏi tôi về câu trả lời tôi đã đăng trên các giai đoạn đầu tiên của mình trên Stack Overflow. Bạn có thực sự chờ đợi lời giải thích về điều đó?
Maroun

@NickCardoso Tôi KHÔNG cố gắng cung cấp một cái cớ cho bạn cả. Nhận xét của bạn và downvote, sẽ không thay đổi bất cứ điều gì cho đến bây giờ. Đó là những gì tôi đã quyết định BỐN năm trước, tôi không thấy ý nghĩa của việc đưa ra điều này bây giờ :)
Maroun

16

Một cách tiếp cận thô hơn mà không sử dụng phương pháp Arrays.sort sắp xếp. Đây là sử dụng sắp xếp chèn.

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
câu hỏi yêu cầu cách bản địa trong java, không sử dụng bất kỳ thuật toán sắp xếp nào khác.
Vikrant Goel

1
Bỏ phiếu vì đó là một giải pháp hữu ích, không phải vì đó là câu trả lời được yêu cầu.
Chris

1
@VikrantGoel "Cách bản địa trong java" - điều gì không bản địa về phương pháp này? tôi không thấy bất kỳ yêu cầu của bên thứ 3. Phải không
Nick Cardoso

Đây phải là câu trả lời chính xác. Giống như @NickCardoso đã nói ... không có gì là "Cách riêng trong java" hơn thế này.
Mariano Zorrilla

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

Lưu ý rằng điều này sẽ không hoạt động như mong đợi nếu đó là Chuỗi trường hợp hỗn hợp (Nó sẽ đặt chữ hoa trước chữ thường). Bạn có thể truyền một bộ so sánh cho phương thức Sắp xếp để thay đổi điều đó.


1
bạn cần nhập java.util.Arays; nếu không nó sẽ không hoạt động
phễu

3

Thủ tục:

  1. Đầu tiên, chuyển đổi chuỗi thành mảng char
  2. Sau đó sắp xếp mảng ký tự
  3. Chuyển mảng ký tự thành chuỗi
  4. In chuỗi

Đoạn mã:

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

Đây co phải la một tro đua? Đăng câu trả lời giống hệt cho một câu hỏi 8 tuổi? Thật lười biếng.
Nick Cardoso

Tôi không biết gì. Tha thứ cho tôi.
ban

2

Câu hỏi: sắp xếp một chuỗi trong 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

Không sử dụng Bộ sưu tập trong 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);
    }
}

Đầu ra:

nhập chuỗi ==

phân loại

sau khi sắp xếp == ginorst


Bạn nên xem lại tại> =. Điều gì xảy ra với "mnmnmnm" là chuỗi của bạn?
Nick Cardoso
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.