首页 > 解决方案 > 如何从文件中的句子创建随机字符串轮换?

问题描述

如何使用随机方式在文件中的句子创建特定顺序的句子?例如:假设我有一个带有“香蕉橙苹果桃子”的 txt 文件

我想用“橙子、苹果、桃子、香蕉”、“苹果、桃子、香蕉、橙子”等创建一个数组。这就像让它们以新的随机顺序重新组织并将其存储到新文件或数组或其他任何东西。我的主要问题是每次都下一个新的随机订单。我该怎么做?

到目前为止,我编写的代码仅按顺序返回文件中的内容。

private static void sendSentences() {
        String sentence;
        try{
            try(
                    InputStream fis = new FileInputStream("C:\\Users\\.....tweets.txt");
                    InputStreamReader isr = new InputStreamReader(fis, Charset.forName("Cp1252"));
                    BufferedReader br = new BufferedReader(isr);
            ){
                while ((sentence = br.readLine()) != null){
                    sendTweet(sentence, thandle);
                    System.out.println("sent " + sentence + ".");
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        }

    }

标签: java

解决方案


这是使用Fisher-Yates shuffle algorithm的解决方案的概要。这个想法是为每个生成的随机顺序计算一个哈希值,并使用该哈希值来检查该顺序是否重复

public static void main(String[] args) {
    String[] words = new String[] {"bananas", "oranges", "apples", "peaches"};
    int randomCount = 10; //this needs to <= (words.length)!

    Iterator<String[]> randomIterator = new Iterator<>() {
        Set<Integer> hashes = new HashSet<>();

        @Override
        public boolean hasNext() {
            return hashes.size() < randomCount;
        }

        @Override
        public String[] next() {
            int i = words.length;
            while(i > 1) {
                i--;
                int j = new Random().nextInt(i + 1);
                String temp = words[i];
                words[i] = words[j];
                words[j] = temp;
            }
            int h = Arrays.hashCode(words);
            if(hashes.contains(h)) next();
            hashes.add(h);
            return words;
        }
    };

    int c = 1;
    while(randomIterator.hasNext()) {
        System.out.println(c++ +  " "  + Arrays.toString(randomIterator.next()));
    }
}

这输出:

1 [apples, oranges, bananas, peaches]
2 [apples, peaches, bananas, oranges]
3 [oranges, apples, peaches, bananas]
4 [bananas, peaches, oranges, apples]
5 [bananas, oranges, apples, peaches]
6 [oranges, bananas, apples, peaches]
7 [apples, bananas, peaches, oranges]
8 [peaches, apples, oranges, bananas]
9 [peaches, oranges, bananas, apples]
10 [bananas, apples, peaches, oranges]

使用迭代器,我们可以确保在我们必须重复一个模式之前,只根据需要执行洗牌算法的次数。您可以将输入/输出机制更改为您想要的方法。

这可以根据用例进行改进。例如,您可以在所有模式生成一次时清空哈希集,并StackOverflow Error通过遍历n! 来避免错误!重复。正如另一个答案所暗示的那样,您也可以使用 aList而不是 anArray并使用Collections.shuffle()来获得新的随机顺序。


推荐阅读