Java随机点名器(带权重的随机算法)

绝地灬酷狼 2024-04-22 05:21 127阅读 0赞

通过带权重的随机算法来实现随机点名器,该点名器的效果是点到的学生再次被点到的概率下降一半。

核心思想:给每个学生设置权重,初始权重全部为1.0,计算权重总和和学生实际的占比,然后在创建数组来模拟权重范围,例如:

arr = {1.0,2.0,3.0,4.0,5.0,6.0},那么如果随机数随机到3.14,则表示点到的学生位于3.0-4.0之间,在返回数组中3.14这个数应存入位置的索引来表示是第几个学生被点到了。

第一个同学范围:【0-1.0)

第二个同学范围:【1.0-2.0)

第三个同学范围:【2.0-3.0)…

以此类推,当同学被点到的之后修改同学对于的权重,修改为原来的一半即可。

  1. /*
  2. * 需求:
  3. * 用程序实现随机点名器。
  4. * 要求点到的学生再次被点到的概率下降一半
  5. * 需要读取本地文件中的数据
  6. * 数据格式:XXX-男-20-1.0
  7. * 分别表示:姓名-性别-年龄-权重占比
  8. * */
  9. 代码实现:
  10. 创建学生类:
  11. package RamdomRollCaller;
  12. public class Student {
  13. private String name;
  14. private String gender;
  15. private int age;
  16. private double weight;
  17. public Student() {
  18. }
  19. public Student(String name, String gender, int age, double weight) {
  20. this.name = name;
  21. this.gender = gender;
  22. this.age = age;
  23. this.weight = weight;
  24. }
  25. public String getName() {
  26. return name;
  27. }
  28. public void setName(String name) {
  29. this.name = name;
  30. }
  31. public String getGender() {
  32. return gender;
  33. }
  34. public void setGender(String gender) {
  35. this.gender = gender;
  36. }
  37. public int getAge() {
  38. return age;
  39. }
  40. public void setAge(int age) {
  41. this.age = age;
  42. }
  43. public double getWeight() {
  44. return weight;
  45. }
  46. public void setWeight(double weight) {
  47. this.weight = weight;
  48. }
  49. @Override
  50. public String toString() {
  51. return name + "-" + gender + "-" + age + "-" + weight;
  52. }
  53. }

完整代码实现:

  1. package RamdomRollCaller;
  2. import java.io.*;
  3. import java.lang.reflect.AnnotatedArrayType;
  4. import java.util.ArrayList;
  5. import java.util.Arrays;
  6. public class RollCallerDemo5 {
  7. /*
  8. * 需求:
  9. * 用程序实现随机点名器。
  10. * 要求点到的学生再次被点到的概率下降一半
  11. * 需要读取本地文件中的数据
  12. * 数据格式:XXX-男-20-1.0
  13. * 分别表示:姓名-性别-年龄-权重占比
  14. * */
  15. public static void main(String[] args) throws IOException {
  16. //关联本地文件
  17. BufferedReader br = new BufferedReader(new FileReader("b.txt"));
  18. //创建集合用于临时存储数据
  19. ArrayList<String> nameTempList = new ArrayList<>();
  20. //创建集合存储学生对象便于管理和操作
  21. ArrayList<Student> students = new ArrayList<>();
  22. //读数据
  23. String str = "";
  24. while ((str = br.readLine()) != null) {
  25. nameTempList.add(str);
  26. }
  27. //关流
  28. br.close();
  29. //获取数据内容并创建学生对象添加到集合
  30. for (String nameStr : nameTempList) {
  31. String[] arr = nameStr.split("-");
  32. students.add(new Student(arr[0], arr[1], Integer.parseInt(arr[2]), Double.parseDouble(arr[3])));
  33. }
  34. //计算总比重
  35. double weight = 0;
  36. for (Student student : students) {
  37. weight = weight + student.getWeight();
  38. }
  39. //计算每个人的实际占比
  40. double[] arr = new double[students.size()];
  41. int index = 0;
  42. for (Student student : students) {
  43. arr[index] = student.getWeight() / weight;
  44. index++;
  45. }
  46. //计算每个人的占比范围
  47. for (int i = 1; i < arr.length; i++) {
  48. arr[i] = arr[i] + arr[i - 1];
  49. }
  50. //制造0-1.0的随机数
  51. double random = Math.random();
  52. //二分查找,计算出随机数应存入的位置
  53. //细节:调用Arrays的二分查找方法,该方法返回负的索引值减一
  54. // 要得到最终索引需要反向操作,用返回值的相反数减一得到被点到的学生对象在students集合中的位置
  55. int i = -Arrays.binarySearch(arr, random) - 1;
  56. Student result = students.get(i);
  57. System.out.println(result.getName());
  58. //修改该学生的占比
  59. double w = result.getWeight() / 2;
  60. result.setWeight(w);
  61. //将修改后的数据写到源文件中
  62. BufferedWriter bw = new BufferedWriter(new FileWriter("b.txt"));
  63. for (Student s : students) {
  64. bw.write(s.toString());
  65. bw.newLine();
  66. }
  67. //关流
  68. bw.close();
  69. }
  70. }

运行效果:

671beaf83856403a81e9f2b1c608c402.png

随机到的同学占比修改为0.5,再次运行程序:

586039f3f6134cda8226357361958790.png

发表评论

表情:
评论列表 (有 0 条评论,127人围观)

还没有评论,来说两句吧...

相关阅读

    相关 Java实现随机点名

    细节1:假设班级有5名同学,每轮中的每一位同学只能被点到一次,程序运行五次,第一轮点名结束。* 细节2:第6次运行的时候,我们自己不需要手动操作本地文件,要求...

    相关 Java随机点名案例

    随机点名器,即在全班同学中随机的打印出一名同学的名字。 要做到随机点名,需要具备 ①存储所有的同学姓名 ②显示全班同学姓名 ③随机点名其中的一个人,打印到控制台。 需要涉及

    相关 随机选择算法

    一个新的功能上线都会走灰度的过程,万一新功能有问题,则会导致线上的大量的报错,甚至不可用的严重情况。比如我们现在本来接入了2个短信渠道去发送短信,现在接入好了第三个渠道,如果我