Java 如何打乱字符串中的字符

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/3316674/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-13 22:02:32  来源:igfitidea点击:

How to shuffle characters in a string

java

提问by user339108

How do I shuffle the characters in a string (e.g. hello could be ehlol or lleoh or ...). I don't want to use the Collections.shuffle(...)method, is there anything simpler?

我如何打乱字符串中的字符(例如,hello 可以是 ehlol 或 lleoh 或 ...)。我不想用这个Collections.shuffle(...)方法,有没有更简单的方法?

采纳答案by bragboy

I dont know anything simpler. But you can use the Math.rand() functionality to generate a random number within the range of the character's length without replace and that would give you a shuffled output

我不知道什么更简单。但是您可以使用 Math.rand() 功能在字符长度范围内生成一个随机数而无需替换,这会给您一个混洗的输出

public class Shuffle {
    public static void main(String[] args) {
        Shuffle s = new Shuffle();
        s.shuffle("hello");

    }
    public void shuffle(String input){
        List<Character> characters = new ArrayList<Character>();
        for(char c:input.toCharArray()){
            characters.add(c);
        }
        StringBuilder output = new StringBuilder(input.length());
        while(characters.size()!=0){
            int randPicker = (int)(Math.random()*characters.size());
            output.append(characters.remove(randPicker));
        }
        System.out.println(output.toString());
    }
}
/*
Sample outputs
hlleo
llheo
leohl
lleho
*/

回答by Tarski

You could iterate over all the characters, comparing each one with the next. Then if Math.rand() > 0.5 swap this character with the next, otherwise move on to the next character.

您可以遍历所有字符,将每个字符与下一个进行比较。然后如果 Math.rand() > 0.5 将这个字符与下一个交换,否则移动到下一个字符。

回答by amra

E.g.:

例如:

static String shuffle(String text){
    if (text.length()<=1)
        return text;

    int split=text.length()/2;

    String temp1=shuffle(text.substring(0,split));
    String temp2=shuffle(text.substring(split));

    if (Math.random() > 0.5) 
        return temp1 + temp2;
    else 
        return temp2 + temp1;
}    

回答by user272043

class ShuffleString
{

    public static String shuffle(String s)
    {

        String shuffledString = ""; 

        while (s.length() != 0)
        {
            int index = (int) Math.floor(Math.random() * s.length());
            char c = s.charAt(index);
            s = s.substring(0,index)+s.substring(index+1);
            shuffledString += c;
        }

        return shuffledString;

    }

}


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

        String test = "hallo";
        test = ShuffleString.shuffle(test);
        System.out.println(test);
    }
}

Output: ahlol

输出:ahlo

回答by Nick Bolton

Not great performance, but quite readable in my opinion:

不是很好的表现,但在我看来相当可读:

public static String shuffleString(String string)
{
  List<String> letters = Arrays.asList(string.split(""));
  Collections.shuffle(letters);
  String shuffled = "";
  for (String letter : letters) {
    shuffled += letter;
  }
  return shuffled;
}

回答by Karl Giesing

Here's code that requires neither recursion, nor converting to a Collection.

这是既不需要递归也不需要转换为集合的代码。

public static String shuffle(String string) {
    StringBuilder sb = new StringBuilder(string.length());
    double rnd;
    for (char c: string.toCharArray()) {
        rnd = Math.random();
        if (rnd < 0.34)
            sb.append(c);
        else if (rnd < 0.67)
            sb.insert(sb.length() / 2, c);
        else
            sb.insert(0, c);
    }       
    return sb.toString();
}

回答by mac

Not sure why you wouldn't want to use shuffle, unless it's for school. ;)

不知道为什么你不想使用 shuffle,除非它是为了学校。;)

And if you're concerned with performance, you definitely can't use any solution that concatenates strings with "+".

如果你关心性能,你绝对不能使用任何用“+”连接字符串的解决方案。

Here's the most compact solution I could come up with:

这是我能想到的最紧凑的解决方案:

public static String shuffle(String string) {
    if (StringUtils.isBlank(string) {
        return string;
    }

    final List<Character> randomChars = new ArrayList<>();
    CollectionUtils.addAll(randomChars, ArrayUtils.toObject(string.toCharArray()));
    Collections.shuffle(randomChars);
    return StringUtils.join(randomChars, "");
}

回答by cherouvim

How about this:

这个怎么样:

public static String shuffle(String text) {
    char[] characters = text.toCharArray();
    for (int i = 0; i < characters.length; i++) {
        int randomIndex = (int)(Math.random() * characters.length);
        char temp = characters[i];
        characters[i] = characters[randomIndex];
        characters[randomIndex] = temp;
    }
    return new String(characters);
}

回答by s13o

        String shuffled;
        do {
            shuffled = Stream.of(text.split("")).sorted((o1, o2) -> ThreadLocalRandom.current().nextInt(3) - 1).collect(Collectors.joining());
        }while(shuffled.equals(text));

回答by Chris

What an annoying problem. I finally ended up with this:

多么烦人的问题。我最终得到了这个:

import java.util.Collections;
import com.google.common.primitives.Chars;
import org.apache.commons.lang3.StringUtils;

String shuffle(String s) {
    List<Character> chars = Chars.asList(s.toCharArray());
    Collections.shuffle(chars);
    return StringUtils.join(chars.stream().toArray());
}

Yes, two libraries :)

是的,两个图书馆:)