不记得在哪看到这个问题,突然有了兴趣,所以试试。
题意: 一个房间内有100个人,每人都有100块钱,每过1分钟,每个人拿1块钱,随机给其他人。你觉得一段时间后,每个人的钱是怎么样的?
看完题后我第一反应是 不是应该每个人都还有差不多100块吗?
所以我写了个程序跑一下。结果出乎我的意料。
数据我用表格统计出来了
没想到运气最好的那个 既然金额达到200, 其他最少的 已经降到15左右
然后我在想是什么导致 方差变大的? 结果我发现是时间
时间越久方差越大。 穷鬼越穷。 富裕的越有钱
数据如下
真的是 马太效应:强者越强,弱者越弱
下面是我Java源代码 是论坛上一大神写的 我按照我的思路改了
package idea.$for100;
import java.util.ArrayList;
import java.util.Date;
import java.util.Random;
public class ExchangeHome implements Runnable{
public static String [] m = new String [10];
//设置三个常量的目的是减小样本数,方便调试,正式版只需要将常量值修改为系统要求即可
/**
* 系统运行时间,单位:秒
*/
public static int TOTAL_TIME = 1000;
/**
* 每次交换的时间间隔,单位:秒
*/
public static int SPACE_TIME = 1;
/**
* 系统中的总人数
*/
public static int USER_COUNT = 10;
/**
* 当前时间,单位:秒
*/
public static int curTime = 0;
/**
* 系统中全部用户的列表
*/
private ArrayList<User> userList;
public ExchangeHome(){
userList = new ArrayList<User>();
User user;
for(int i=0;i<USER_COUNT; i++){
user = new User(i);
userList.add(user);
}
}
public static void main(String[] args) {
ExchangeHome home = new ExchangeHome();
new Thread(home).run();
// System.out.println("--- end ---");
String m2 [] = new String [10];
int max = 0; int min = Integer.MAX_VALUE;int count=0;
int maxid = 0; int minid = 0;
for(int i=0;i<m.length;i++){
// System.out.println(m[i]);
m2[i] = m[i].substring(m[i].lastIndexOf(">")+1);
int temp = Integer.parseInt(m2[i]);
System.out.println(temp);
if(temp>max){
max = temp;
maxid = i;
}
if(temp<min){
min = temp;
minid = i;
}
if(temp>=100){
count++;
}
}
// System.out.println(maxid+1);
// System.out.println(minid+1);
// System.out.println(max);
// System.out.println(min);
}
@Override
public void run() {
while(curTime <=TOTAL_TIME){
try {
User payer;
User receiver;
int receiverId;
// System.out.println("______");
for( int i=0;i<USER_COUNT;i++){
payer = userList.get(i);
if(payer.getMoney()<=0){
continue;
}
//随机选取一个用户
Random r = new Random( new Date().getTime());
// receiverId = (int) Math.floor(Math.random()*(userList.size()-1));
receiverId = r.nextInt(10);
// if(receiverId >=1 ){
// //随机到当前用户或者之后的用户,将该ID加一,以保证不会给自己1元钱,并保证所有用户获得馈赠的概率相当
// receiverId += 1;
// }
while(i == receiverId){
receiverId = r.nextInt(10);
}
receiver = userList.get(receiverId);
payer.give(receiver);
m[payer.getId()] = m[payer.getId()]+"->"+payer.getMoney();
// System.out.println(payer.getId()+"("+payer.getMoney()+") -->" + receiver.getId()+"("+receiver.getMoney()+")");
}
Thread.sleep(SPACE_TIME*10);
curTime += SPACE_TIME;
} catch (Exception e) {
}
}
}
}
/**
* 用户类
*/
class User{
/**
* 用户的钱数
*/
private int money = 100;
/**
* 用户的ID
*/
private int id;
public User(int id) {
this.id = id;
}
/**
* 当前用户给目标用户一定量的钱
* @param user
*/
public void give(User user){
// 这里应该考虑事物管理
this.pay(1);
user.receive(1);
}
/**
* 接收一定数目的钱
* @param i
*/
public void receive(int v) {
money += v;
}
/**
* 支付一定数目的钱
* @param v
*/
public void pay(int v) {
money -= v;
}
/**
* 获取用户当前持有的钱数
* @return
*/
public int getMoney(){
return money;
}
/**
* 获取用户的ID
* @return
*/
public int getId(){
return id;
}
}