Как перетасовать символы в строке в JavaScript? - PullRequest
38 голосов
/ 15 октября 2010

В частности, я хочу избежать ошибки, допущенной в коде тасования Microsoft Browser Choice. То есть я хочу убедиться, что каждая буква имеет одинаковую вероятность оказаться в каждой возможной позиции.

например. Учитывая "ABCDEFG", вернуть что-то вроде "GEFBDCA".

Ответы [ 8 ]

70 голосов
/ 15 октября 2010

Я изменил пример из записи Fisher-Yates Shuffle в Википедии , чтобы перемешать строки:

String.prototype.shuffle = function () {
    var a = this.split(""),
        n = a.length;

    for(var i = n - 1; i > 0; i--) {
        var j = Math.floor(Math.random() * (i + 1));
        var tmp = a[i];
        a[i] = a[j];
        a[j] = tmp;
    }
    return a.join("");
}
console.log("the quick brown fox jumps over the lazy dog".shuffle());
//-> "veolrm  hth  ke opynug tusbxq ocrad ofeizwj"

console.log("the quick brown fox jumps over the lazy dog".shuffle());
//-> "o dt hutpe u iqrxj  yaenbwoolhsvmkcger ozf "

Дополнительную информацию можно найти в Ответ Джона Скита на Правильно ли использовать метод JavaScript Array.sort () для перемешивания? .

37 голосов
/ 13 ноября 2012

Если важна «истинно» случайность, я рекомендую против этого. См. Мое редактирование ниже.

Я просто хотел добавить свой любимый метод для небольшого разнообразия;)

С учетом строки:

var str = "My bologna has a first name, it's O S C A R.";

Перестановка в одну строку:

var shuffled = str.split('').sort(function(){return 0.5-Math.random()}).join('');

Выходы:

oa, a si'rSRn f gbomi. aylt AtCnhO ass eM
as'oh ngS li Ays.rC nRamsb Oo ait a ,eMtf
y alCOSf e gAointsorasmn bR Ms .' ta ih,a

РЕДАКТИРОВАТЬ: Как отметил @PleaseStand, это не отвечает на вопрос OP, так как он страдает от кода "Microsoft Browser Choice shuffle". Это не очень хороший рандомизатор, если ваша строка должна быть близка к случайной. Тем не менее, это удивительно - быстро «перемешивать» ваши строки, где «истинная» случайность не имеет значения.

Статья, на которую он ссылается ниже, отлично читается, но объясняет совершенно другой вариант использования, который влияет на статистические данные. Лично я не могу представить практическую проблему с использованием этой «случайной» функции для строки, но как кодер, вы должны знать, когда не использовать это.

Я оставил это здесь для всех случайных рандомизаторов.

6 голосов
/ 01 декабря 2015

Несмотря на то, что на этот вопрос уже получен ответ, я хотел поделиться предложенным решением:

function shuffelWord (word){
    var shuffledWord = '';
    word = word.split('');
    while (word.length > 0) {
      shuffledWord +=  word.splice(word.length * Math.random() << 0, 1);
    }
    return shuffledWord;
}

// 'Batman' => 'aBmnta'

Вы также можете попробовать его (jsfiddle) .

0 голосов
/ 25 июня 2019

Если вы любите аккуратные и красивые однострочники, как я, вам может понравиться моя реализация ES6:

const str = 'ABCDEFG';

const shuffle = str => [...str].reduceRight((res,_,__,arr) => [...res,arr.splice(~~(Math.random()*arr.length),1)[0]],[]).join('');

console.log(shuffle(str));
0 голосов
/ 19 мая 2019

Другой подход к набору слов. Все остальные ответы с достаточным количеством итераций вернут слово без шифрования, а у меня - нет.

var scramble = word => {

    var unique = {};
    var newWord = "";
    var wordLength = word.length;

    word = word.toLowerCase(); //Because why would we want to make it easy for them?

    while(wordLength != newWord.length) {

        var random = ~~(Math.random() * wordLength);

        if(

          unique[random]
          ||
          random == newWord.length && random != (wordLength - 1) //Don't put the character at the same index it was, nore get stuck in a infinite loop.

        ) continue; //This is like return but for while loops to start over.

        unique[random] = true;
        newWord += word[random];

    };

    return newWord;

};

scramble("God"); //dgo, gdo, ogd
0 голосов
/ 07 ноября 2017
String.prototype.shuffle = function(){
  return this.split('').sort(function(a,b){
    return (7 - (Math.random()+'')[5]);
  }).join('');
};
0 голосов
/ 21 октября 2015
                  shuffleString = function(strInput){
                     var inpArr = strInput.split("");//this will give array of input string
                     var arrRand = []; //this will give shuffled array
                     var arrTempInd = []; // to store shuffled indexes
                     var max = inpArr.length;
                     var min = 0;
                     var tempInd;
                     var i =0 ;

                      do{
                           tempInd = Math.floor(Math.random() * (max - min));//to generate random index between range
                           if(arrTempInd.indexOf(tempInd)<0){ //to check if index is already available in array to avoid repeatation
                                arrRand[i] = inpArr[tempInd]; // to push character at random index
                                arrTempInd.push(tempInd); //to push random indexes 
                                i++;
                            }
                       }
                        while(arrTempInd.length < max){ // to check if random array lenght is equal to input string lenght
                            return arrRand.join("").toString(); // this will return shuffled string
                        }
                 };

Просто передайте строку в функцию и взамен получите перемешанную строку

0 голосов
/ 21 августа 2014
String.prototype.shuffle=function(){

   var that=this.split("");
   var len = that.length,t,i
   while(len){
    i=Math.random()*len-- |0;
    t=that[len],that[len]=that[i],that[i]=t;
   }
   return that.join("");
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...