写点什么

一个数组通过配置随机抽取组成小数组

发布于: 2021 年 03 月 31 日

1.场景


现有一个数组,想抽出其中一部分元素组成另外一个小一点的数组,又不希望完全随机抽出,比如希望原数组的前 20%抽多点,中间的 50%少抽点,最后的 30%再多抽点,而且希望在范围内是不重复随机抽取


2.思路将不同的配置,转化成固定要取的数量的区域,再从不同的区域里使用不重复随机算法取


3.Java Code


package kowalski;
import java.util.ArrayList;import java.util.Collections;import java.util.HashMap;import java.util.List;import java.util.Map;import java.util.Random;import java.util.concurrent.ThreadLocalRandom;
/** * Created by kowalski.zhang on 2018/6/6 */public final class PickUtil {
private static Random random = ThreadLocalRandom.current();
private PickUtil() { }
/*** * just pick with config * @param srcList * @param configs * @param <T> * @return */ public static <T> List<T> levelPickWithNewByConfig(List<T> srcList, Double[]... configs) {
if (srcList == null || srcList.isEmpty()) { return Collections.emptyList(); } List<T> res = new ArrayList<>(srcList.size());
int lastIndex = 0; for (Double[] config : configs) {
int modelLen = config[0].intValue(); /**获取长度大于等于有效长度 全额取出*/ if (modelLen <= config[1]) { for (int m = 0; m < modelLen; m++) { res.add(srcList.get(lastIndex + m)); } } else { /**区域内使用不重复随机算法pick*/ int randLen = config[1].intValue(); int tempModelLen = modelLen; for (int m = 0; m < randLen; m++) { int randNum = random.nextInt(tempModelLen); res.add(srcList.get(randNum + lastIndex)); tempModelLen--; } } lastIndex += modelLen; }
return res; }
/** * pick * @param srcList * @param configs 取出配置 * @param pickNum 最大取出量 * @param <T> * @return */ public static <T> List<T> levelPickWithNew(List<T> srcList, Double[][] configs, ConfigTypeEnum typeEnum, Integer pickNum) { if (pickNum < srcList.size()) { return srcList; }
switch (typeEnum){ case FIXED_FIXED: return levelPickWithNewByConfig(srcList, configs); case JUST_PERCENT: return levelPickWithNewByConfig(srcList, exchangeConfigToFixNum(srcList.size(), configs)); case PERCENT_FIXED: return levelPickWithNewByConfig(srcList, exchangeConfigToFixNum(srcList.size(), pickNum, configs)); } return srcList; }
public static <T> List<T> levelPickWithNew(List<T> srcList, Double[][] configs, ConfigTypeEnum typeEnum) { return levelPickWithNew(srcList, configs, typeEnum, null); }
/** * 将ConfigTypeEnum.PERCENT_FIXED转化成对应的FIXED_FIXED配置 * @param listLen * @param configs * @return */ public static Double[][] exchangeConfigToFixNum(int listLen, Double[]... configs) { Double[][] res = new Double[configs.length][configs[0].length]; int total = 0; for (int i = 0; i < configs.length - 1; i++) { int temp = (int) (configs[i][0] * listLen); total += temp; res[i][0] = (double) temp; } /**最后一个配置收拾残局*/ if (listLen > total) { res[configs.length - 1][0] = (double) (listLen - total); } return res; }
/*** * ConfigTypeEnum.JUST_PERCENT转化成对应的FIXED_FIXED配置 * @param listLen * @param pickNum * @param configs */ public static Double[][] exchangeConfigToFixNum(int listLen, Integer pickNum, Double[]... configs) {
if (pickNum == null || pickNum < 0) { throw new RuntimeException("pickNum not leagal !!!"); } Double[][] res = new Double[configs.length][configs[0].length]; int total = 0; int totalPick = 0; for (int i = 0; i < configs.length - 1; i++) { int temp = (int) (configs[i][0] * listLen); int tempPick = (int) (configs[i][0] * pickNum); total += temp; totalPick += tempPick; res[i][0] = (double) temp; res[i][1] = (double) tempPick; } /**最后一个配置收拾残局*/ if (listLen > total) { res[configs.length - 1][0] = (double) (listLen - total); } if (pickNum > totalPick) { res[configs.length - 1][1] = (double) (pickNum - totalPick); }
return res; }
public enum ConfigTypeEnum {
PERCENT_FIXED(1, "百分比-固定量"), FIXED_FIXED(2, "固定量-固定量"), JUST_PERCENT(4, "仅百分比"),;//必须传期待List大小(pickNum)
private Integer type; private String desc;
ConfigTypeEnum(Integer type, String desc) { this.type = type; this.desc = desc; }
public Integer getType() { return type; }
public void setType(Integer type) { this.type = type; }
public String getDesc() { return desc; }
private static final Map<Integer, ConfigTypeEnum> map = new HashMap<>();
static { for (ConfigTypeEnum enums : ConfigTypeEnum.values()) { map.put(enums.getType(), enums); } }
public static ConfigTypeEnum getEnumValue(int code) { return map.get(code); }
public static String getDescByType(int code) { return map.get(code).getDesc(); }
public void setDesc(String desc) { this.desc = desc; }
}

public static void main(String... args) {
Double[][] configs = { { 0.15d, 10.0d }, { 0.25d, 15.0d }, { 0.6d, 30.0d } };
ConfigTypeEnum configType = ConfigTypeEnum.PERCENT_FIXED; }}
复制代码


有更好方式的小伙伴欢迎交流~~e:995517265@qq.com

发布于: 2021 年 03 月 31 日阅读数: 9
用户头像

还未添加个人签名 2020.03.30 加入

还未添加个人简介

评论

发布
暂无评论
一个数组通过配置随机抽取组成小数组