Подскажите, что не так:
тестировал раз 50, всегда присутствует и цифра, и латинская заглавная, и латинская строчная. И всегда 8 символов.
алгоритм такой:
1. Вычисляю рандомно три числа: колчество цифр, количество строчных букв, количество заглавных букв.
2. Подгоняю рандомно сумму этих трех чисел до 8.
3. Создаю 3 массива char[] - коды цифр, коды строчных букв, коды заглавных букв.
4. Создаю результирующий массив Character[] symbols = new Character[8]; из 8 символов.
5. Заполняю по порядку результирующий массив -
5.1. сначала произвольными цифрами из массива кодов цифр в количестве из 1-го пункта.
5.2. потом произвольными заглавными
5.2. потом произвольным истрочными.
6. Перегоняю этот результирующий массив в колллекцию List<Character> list = Arrays.asList(symbols); и делаю Collections.shuffle(list);
7. Из перемешанной коллекции строю в цикле новый StringBuilder
8. Из этого StringBuilder получаю ByteArrayOutputStream() и возвращаю его.
package com.javarush.task.task32.task3204;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
/*
Генератор паролей
*/
public class Solution {
public static void main(String[] args) {
ByteArrayOutputStream password = getPassword();
System.out.println(password.toString());
}
public static ByteArrayOutputStream getPassword() {
//48 - 57 - иапазон цифр - коды unicode
//65 - 90 - диапазон латиница - заглавные.
//97 - 122 - диапазон латиница - маленькие
//количество цифр в пароле:
int countNumbers = (int)(Math.random() * 5 + 1); //от 1 до 6
//количество заглавных букв в пароле:
int countLettersCaps = (int)(Math.random() * 5 + 1); //от 1 до 6
//количество строчных букв в пароле:
int countLettersLow = (int)(Math.random() * 5 + 1); //от 1 до 6
//сумма цифр и заглавных букв не должна превышать 7 (оставить место для хотя бы одной строчной буквы)
while((countLettersCaps + countNumbers) > 7){
//случайная величина boolean - если true - уменьшаем countNumbers, иначе уменьшаем countLettersCaps
boolean choice;
int n = (int)(Math.random() * 10) ;
if(n%2 == 0){
choice = true;
}
else{
choice = false;
}
if(choice){
//уменьшаем countNumbers
countNumbers--;
}else{
//уменьшаем
countLettersCaps--;
}
}
//сумма всех символов не должна превышать 8:
while(countLettersCaps + countNumbers + countLettersLow > 8){
int choice = (int)(Math.random() * 3) ;
switch (choice){
case 0: countLettersCaps--;
case 1: countNumbers--;
case 2: countLettersLow--;
}
}
//если символов меньше восьми - добавить каждому по-чутка в цикле.
while(countLettersCaps + countNumbers + countLettersLow < 8){
int choice = (int)(Math.random() * 3) ;
switch (choice){
case 0: countLettersCaps++;
case 1: countNumbers++;
case 2: countLettersLow++;
}
}
//48 - 57 - диапазон цифр - коды unicode
//массив кодов символов цифр
char[] numbers = {48, 49, 50, 51, 52, 53, 54, 55, 56, 57};
//массив кодов заглавных букв:
//65 - 90 - диапазон латиница - заглавные.
char[] capLetters = new char[26];
int index = 0;
for(int i = 65; i <= 90; i++){
capLetters[index] = (char)i;
index ++;
}
//массив кодов строчных букв
//97 - 122 - диапазон латиница - маленькие
char[] lowLetters = new char[26];
index = 0;
for(int i = 97; i <= 122; i++){
lowLetters[index] = (char)i;
index ++;
}
//массив символов пароля:
Character[] symbols = new Character[8];
//1. заполнить произвольными цифрами из массива numbers в размере countNumbers:
for(int i = 0; i < countNumbers; i++){
char randomChar = numbers[(int)(Math.random() * numbers.length)];
symbols[i] = randomChar;
}
// /////////////////////////////////////////////////////////////////
// System.out.println("заполнить произвольными цифрами из массива numbers в размере countNumbers:");
// System.out.println(Arrays.toString(symbols));
// /////////////////////////////////////////////////////////////////
//2. заполнить произвольными заглавными буквами в размере countLettersCaps:
for(int i = countNumbers; i < countNumbers + countLettersCaps; i++){
char randomChar = capLetters[(int)(Math.random() * capLetters.length)];
symbols[i] = randomChar;
}
// /////////////////////////////////////////////////////////////////
// System.out.println("заполнить произвольными заглавными буквами в размере countLettersCaps:");
// System.out.println(Arrays.toString(symbols));
// /////////////////////////////////////////////////////////////////
//3. заполнить произвольными строчными буквами в размере countLettersLow:
for(int i = countNumbers + countLettersCaps; i < 8; i++){
char randomChar = lowLetters[(int)(Math.random() * lowLetters.length)];
symbols[i] = randomChar;
}
// /////////////////////////////////////////////////////////////////
// System.out.println("заполнить произвольными строчными буквами в размере countLettersLow:");
// System.out.println(Arrays.toString(symbols));
// /////////////////////////////////////////////////////////////////
//4. перегнать в коллекцию и сделать shuffle();
List<Character> list = Arrays.asList(symbols);
Collections.shuffle(list);
//5. перегнать в ByteArrayOutputStream и вернуть
StringBuilder sb = new StringBuilder();
for(Character c : list){
sb.append(c);
}
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
try {
byteArrayOutputStream.write(sb.toString().getBytes());
} catch (IOException e) {
e.printStackTrace();
}
return byteArrayOutputStream;
}
}