Javascript-форум (https://javascript.ru/forum/)
-   Общие вопросы Javascript (https://javascript.ru/forum/misc/)
-   -   Замена одинаковых букв приводит к бесконечному циклу? (https://javascript.ru/forum/misc/84440-zamena-odinakovykh-bukv-privodit-k-beskonechnomu-ciklu.html)

Olga27 08.09.2022 12:52

Замена одинаковых букв приводит к бесконечному циклу?
 
Вложений: 1
Пытаюсь заменить одинаковые буквы в массиве, для этого устанавливаю флаг isUniq = false; если буквы неуникальны. Проверка букв проходит в дополнительном цикле do while, в итоге происходит бесконечный цикл и браузер начинает зависать.
Чтобы протестировать, как работает замена я убрала do while и добавила ключевое слово “smena” и вывожу через console.log. В итоге код работает если буквы повторяются то выводится “smena”, как например с буквой “Щ” которая встречается в массиве два раза. Пример на картинке.
Вложение 4822
Однако с флагом происходит зависания браузера из-за невозможности завершить цикл. Как исправить? Вот код:
<!doctype html>
<html lang="en">
<head>
  <meta charset="utf-8">

  <script>
  var bukvy = ['А', 'Б', 'В', 'Г', 'Д', 'Е', 'Ж', 'З',
  'И', 'Й',
  'К', 'Л', 'М', 'Н', 'О', 'П', 'Р',
  'С', 'Т', 'У', 'Ф', 'Х', 'Ц', 'Ч', 'Ш', 'Щ', 'Ъ', 'Ы', 'Ь', 'Э', 'Ю', 'Я'];
  var slovo;
  var word1='лес';
  
  slovo = word1.split("");
  var isUniq; 

     function showInfo()
     {
     
      for (var i = slovo.length; i < 16; i++)
      {
      
             do
              {
               
                isUniq = true;
                word1 = bukvy[Math.trunc(Math.random()*bukvy.length)];
                
                for (var j=0; j<=i-2;j++)
                {
                  
                  if(slovo[j]==word1) 
                  {
                    isUniq = false;
                   // console.log("smena");
                  }
                }
            }while(isUniq)
           
            slovo[i]=word1;
            //console.log(slovo[i]);
            
          
        
      }
     }
  </script> 
</head>
<body onload="showInfo()">  

</body>
</html>

Alexandroppolus 08.09.2022 13:25

а что требуется-то? какая задача?

Olga27 08.09.2022 14:38

Исключить повторяющиеся буквы при заполнении массива.

рони 08.09.2022 15:30

Olga27,
<!doctype html>
<html lang="en">

<head>
    <meta charset="utf-8">
    <script>
        const bukvy = ['А', 'Б', 'В', 'Г', 'Д', 'Е', 'Ж', 'З',
            'И', 'Й',
            'К', 'Л', 'М', 'Н', 'О', 'П', 'Р',
            'С', 'Т', 'У', 'Ф', 'Х', 'Ц', 'Ч', 'Ш', 'Щ', 'Ъ', 'Ы', 'Ь', 'Э', 'Ю', 'Я'
        ];
        let word = 'лес';
        function showInfo(word) {
            let endWord = bukvy.slice(0).sort(_ => .5 - Math.random() ).slice(0, 16 - word.length)
            return word.split("").concat(endWord)
        }
    </script>
</head>

<body onload="alert(showInfo(word));">
</body>

</html>

Olga27 08.09.2022 20:09

А как сделать, чтобы буквы перемешивались пополам, половина согласных и половина гласных (при этом сохраняя уникальность). Притом, что если количество букв нечетное, например “лес” состоит из трех букв (значит остается еще 13 букв которые нужно добавить до 16), то буквы добавлялись в пользу гласных. Например 7 гласных и 6 согласных.

Я добавила две переменные “sogl” и “glasn”.
<!doctype html>
<html lang="en">

<head>
    <meta charset="utf-8">
    <script>
        const bukvy = ['А', 'Б', 'В', 'Г', 'Д', 'Е', 'Ж', 'З',
            'И', 'Й',
            'К', 'Л', 'М', 'Н', 'О', 'П', 'Р',
            'С', 'Т', 'У', 'Ф', 'Х', 'Ц', 'Ч', 'Ш', 'Щ', 'Ъ', 'Ы', 'Ь', 'Э', 'Ю', 'Я'
        ];
        
        const sogl = ['Б', 'В', 'Г', 'Д', 'Ж', 'З',
          'Й', 'К', 'Л', 'М', 'Н', 'П', 'Р', 'С', 'Т', 'Ф', 'Х', 'Ц',
          'Ч', 'Ш', 'Щ', 'Ъ', 'Ь'];
        const glasn = ['А', 'О', 'Э', 'Е', 'И', 'Ы',
          'У', 'Ю', 'Я'];
        
        
        let word = 'лес';
        function showInfo(word) {
            let endWord = bukvy.slice(0).sort(_ => .5 - Math.random() ).slice(0, 16 - word.length)
            return word.split("").concat(endWord)
        }
    </script>
</head>

<body onload="alert(showInfo(word));">
</body>

</html>

рони 08.09.2022 20:32

Olga27,
<!doctype html>
<html lang="en">

<head>
        <meta charset="utf-8">
        <script>
                const sogl = ['Б', 'В', 'Г', 'Д', 'Ж', 'З',
                    'Й', 'К', 'Л', 'М', 'Н', 'П', 'Р', 'С', 'Т', 'Ф', 'Х', 'Ц',
                    'Ч', 'Ш', 'Щ', 'Ъ', 'Ь'];
                const glasn = ['А', 'О', 'Э', 'Е', 'И', 'Ы',
                    'У', 'Ю', 'Я'];
                let word = 'лес';
                function showInfo(word) {
                        let s = sogl.slice(0).sort(_ => .5 - Math.random() );
                        let g = glasn.slice(0).sort(_ => .5 - Math.random() );
                        let length = 16 - word.length;
                        let endWord = Array.from({length}, (_, i) => i % 2 ? s[--i/2] : g[i/2])
                        return word.split("").concat(endWord)
                }
        </script>
</head>

<body onload="alert(showInfo(word));">
</body>

</html>

Olga27 09.09.2022 09:24

Вложений: 1
Все работает, но в слове которое учитывается при добавлении могут присутствовать одинаковые буквы. Например слово “фантаст” встречается две буквы “A”. При переборе случайным образом среди дополнительных букв могут попасться еще одна буква “A”.
Пример на картинке.
Вложение 4824
У меня вопрос можно при переборе, на уникальность также проверять указанное слово, чтобы исключить лишние повторы?
<!doctype html>
<html lang="en">

<head>
    <meta charset="utf-8">
    <script>
      const bukvy = ['А', 'Б', 'В', 'Г', 'Д', 'Е', 'Ж', 'З',
            'И', 'Й',
            'К', 'Л', 'М', 'Н', 'О', 'П', 'Р',
            'С', 'Т', 'У', 'Ф', 'Х', 'Ц', 'Ч', 'Ш', 'Щ', 'Ъ', 'Ы', 'Ь', 'Э', 'Ю', 'Я'
        ];
        
        const sogl = ['Б', 'В', 'Г', 'Д', 'Ж', 'З',
          'Й', 'К', 'Л', 'М', 'Н', 'П', 'Р', 'С', 'Т', 'Ф', 'Х', 'Ц',
          'Ч', 'Ш', 'Щ', 'Ъ', 'Ь'];
        const glasn = ['А', 'О', 'Э', 'Е', 'И', 'Ы',
          'У', 'Ю', 'Я'];
        
        
        
        word = "ФАНТАСТ";
       
        function showInfo(word) {
            let s = sogl.slice(0).sort(_ => .5 - Math.random() );
            let g = glasn.slice(0).sort(_ => .5 - Math.random() );
            let length = 16 - word.length;
            let endWord = Array.from({length}, (_, i) => i % 2 == 0 ? g[i/2] : s[++i/2])
            return word.split("").concat(endWord)
        }
      function Main()
      {
          var t = showInfo(word); 
          
          for(var i = 0; i<t.length; i++)
          {
            document.getElementById("debug").innerHTML += t[i]+"\n";
          }    
      }  
       
        
    </script>
</head>

<body onload="Main()">
<textarea id="debug" rows="20" cols="45"></textarea>
</body>

</html>

рони 09.09.2022 11:36

Olga27,
далее сами )))
<!doctype html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <script>
        const bukvy = ['А', 'Б', 'В', 'Г', 'Д', 'Е', 'Ж', 'З',
            'И', 'Й',
            'К', 'Л', 'М', 'Н', 'О', 'П', 'Р',
            'С', 'Т', 'У', 'Ф', 'Х', 'Ц', 'Ч', 'Ш', 'Щ', 'Ъ', 'Ы', 'Ь', 'Э', 'Ю', 'Я'
        ];
        const sogl = ['Б', 'В', 'Г', 'Д', 'Ж', 'З',
            'Й', 'К', 'Л', 'М', 'Н', 'П', 'Р', 'С', 'Т', 'Ф', 'Х', 'Ц',
            'Ч', 'Ш', 'Щ', 'Ъ', 'Ь'
        ];
        const glasn = ['А', 'О', 'Э', 'Е', 'И', 'Ы',
            'У', 'Ю', 'Я'
        ];
        let word = "ФАНТАСТ";
        const createArr = (arr, word) => arr.slice(0).filter(a => !word.includes(a)).sort(_ => .5 - Math.random());
        function showInfo(word) {
            let s = createArr(sogl, word);
            let g = createArr(glasn, word);
            let length = 16 - word.length;
            let endWord = Array.from({ length }, (_, i) => (i % 2 == 0 ? g[i / 2] : s[++i / 2])||"!");
            return word.split("").concat(endWord);
        }
        function Main() {
            var t = showInfo(word);
            document.getElementById("debug").value = t.join("\n")
        }
        window.addEventListener("load", Main);
    </script>
</head>
<body>
    <textarea id="debug" rows="20" cols="45"></textarea>
</body>
</html>


Часовой пояс GMT +3, время: 10:39.