根据值的频率随机选择一个键

时间:2013-11-04 15:48:15

标签: java hashmap frequency-analysis

我有以下Hashmap:

Map <Country, List<City>> map = new HashMap<Country, List<City>>();

我想随机选择一组国家,条件如下:城市数量较少的国家应该被选中的概率较高。

为了解决这个问题,我想我会创建以下地图:

Map <Country, Integer> map = new HashMap<Country, Integer>();

其中整数表示List<City>的大小。

这样我就可以根据Integer值对Map进行排序,然后选择Integer值较低的国家/地区。

但似乎我在很长的路上这样做,而且它不是很随机。您对如何有效解决这个问题有任何建议吗?

2 个答案:

答案 0 :(得分:2)

这里与遗传算法中使用的技术the roulette wheel selection平行。

实施起来非常简单:

  1. 创建一个国家/地区数组,其大小是所有国家/地区的整数总和
  2. 将每个国家/地区放置在数组中,其中N是城市数
  3. 随机选择数组中的值
  4. 选择的国家的概率等于其城市数量

    编辑:如果城市数量非常大,您可以通过除以最低城市数量来标准化数字,以便每个国家/地区仍然存在于表格中。

答案 1 :(得分:0)

  

我想挑选一组城市数量最少的国家。

然后,您需要按顺序或数量的城市List个国家/地区。为什么不创建包含Country个城市的List

public class Country{
   private final List<String> cityNames = new ArrayList<String>();
   private String name;
   public Country(String n) { name = n; }
   public void addCity(String name){ 
       cityNames.add(name);   // omitting validation
   }
   public List<String> getCityNames(){
       List<String> newList = new ArrayList<String>();
       newList.addAll(cityNames);
       return newList;
   }
   public int numberOfCities(){ 
       return cityNames.size(); 
   }

   public String getName() { return name; }

   @Override
   public String toString(){
      return name + ": Number of Cities = " + cityNames.size();
   }
}

现在,您可以根据此类城市数量对国家/地区列表进行排序

... // inside some method

        Collections.sort(countries, new Comparator<Country>() {
        @Override
        public int compare(Country o1, Country o2) {
            if(o1.numberOfCities() < o2.numberOfCities()){
                return -1;
            }
            if(o1.numberOfCities() > o2.numberOfCities()){
                return 1;
            }
            return 0;
        }
    });

我刚用以下方法对此进行了测试(注意:我向国家/地区添加了“toString()”方法)

public static void main(String[] args) {
    Country usa = new Country("USA");
    Country canada = new Country("Canada");
    Country brazil = new Country("Brazil");
    usa.addCity("Lansing");
    usa.addCity("New York");
    usa.addCity("Los Angeles");
    usa.addCity("Houston");

    canada.addCity("Toronto");

    canada.addCity("Niagra");

    brazil.addCity("Vila Velha");
    brazil.addCity("Rio");
    brazil.addCity("Barbacena");

    List<Country> countries = new ArrayList<Country>();
    countries.add(usa);
    countries.add(brazil);
    countries.add(canada);
    System.out.println("\n\nAfter Sorting...");
    it = countries.iterator();
    while(it.hasNext()){
        System.out.println(it.next());
    }
    Collections.sort(countries, new Comparator<Country>() {
        @Override
        public int compare(Country o1, Country o2) {
            if(o1.numberOfCities() < o2.numberOfCities()){
                return -1;
            }
            if(o1.numberOfCities() > o2.numberOfCities()){
                return 1;
            }
            return 0;
        }
    });

    System.out.println("\n\nAfter Sorting...");
    it = countries.iterator();
    while(it.hasNext()){
        System.out.println(it.next());
    }

}

输出

 Before sorting....
 USA: Number of Cities = 4
 Brazil: Number of Cities = 3
 Canada: Number of Cities = 2


 After Sorting...
 Canada: Number of Cities = 2
 Brazil: Number of Cities = 3
 USA: Number of Cities = 4