解决方案 »

  1.   

    你好,我们现在这个是按照批次生成的,一个批次有很多券,券是15位的,前10位是有规律的,后5位是随机的,我们使用的时候是用后5位来确定某一张券的,我们现在既要保证这个券在本批次不重复,还要在其他批次也不重复,难道要生成前到数据库中先查一遍? 自己构建 一个HashMap,把生成的数据丢进去做唯一检查
    如果内存不够用,调大,如果还是不够,就上缓存服务器,如果没有条件用缓存服务器,就用数据库
      

  2.   

    就是长周期随机数生成嘛,这个不是很难吧
    建议看看这篇文章 “产生伪随机数常用的两种算法”直接用glibc随机数的方法就应该可以满足你的要求,它的循环周期是2^n,n是0~32的整数,比如下面的例子,可以产生不重复的0 ~ 2^28-1(268435455)之间的数
    public static int nextRand(int n) {
    return (1103515245 * n + 12345) & 0x0FFFFFFF;
    }
      

  3.   

    只是五位而已,就算查找也很快啊。百万级的自然有算法可以做到比如,bloom filter 这样的检查 set intersection 的东西
      

  4.   

    建立一个list将所有可能的5位组合放进去。建立随机数,每次从list中取随机数未知的内容,取出后将内容移出list。
      

  5.   

    可不可以这样:
    先将序列号生成,保存到数据库中,表中设置一个布尔类型标志位,用过的是true,没用过的是false;
    需要时检索出10个没用过的序列号(标志位:false),随机抽出一个分配给客户,再将标志位设置true。
    这样的话即不会重复,性能也差不到哪去。
      

  6.   

    我不清楚我的方法 效率怎么样,但是可以建立一张只有主键的表,
    里面把35^5   几千万条数据存进去,吧count 放入缓存,每次用random 取随机行号,
    取出数据的操作之后立马执行删除操作 随即进行count数量减少
    这样可以保证你在几千万数据用完之前不会重复
      

  7.   

    个人建议:  一次性生成 N张券(或者 N个 5位 String 串,保证不重复), 可以用多个表 存储,或者 多个 list 存储 (具体看 数据量有多大),然后  对用户所谓的 “生成”  其实 就是从这些 已经 生成好的数据中 随即的 取一个 ,然后在吧该数据 从存储数据的地方删除。 
      

  8.   

    最多准备支持多少张券?如前面回复
    够不够用?够用的话: 
      /** 最大值 */
      public static final long MAX = 60466176; // 36 ^ 6  /** 乘法用的素数 */
      public static final long P = 15485857;
      
      /** 加法用的素数 */
      public static final long Q = 9007;  /** 编码长度 */
      public static final int LEN = 5;  /** 采用36进制 */
      public static final int RADIX = 36;  /**
       * 编码方法。
       * 
       * @param number
       *          序号
       * @return 5位编码
       * @throws IllegalArgumentException
       *           如果序号超过范围
       */
      public static String encode(int number) {
        if (number <= 0 || number > MAX) {
          throw new IllegalArgumentException();
        }
        long x = ((long) number * P + Q) % MAX;
        char[] codes = new char[LEN];
        Arrays.fill(codes, '0');
        String str = Long.toString(x, RADIX);
        System.arraycopy(str.toCharArray(),
                         0,
                         codes,
                         LEN - str.length(),
                         str.length());
        reverse(codes);
        return new String(codes).toUpperCase();
      }  private static void reverse(char[] codes) {
        for (int i = LEN >> 1; i-- > 0;) {
          codes[i] ^= codes[LEN - i - 1];
          codes[LEN - i - 1] ^= codes[i];
          codes[i] ^= codes[LEN - i - 1];
        }
      }此过程,“理论上”可逆,但是decode算法实际上没法用——太慢,几乎等同于把所有可能的值再去encode一遍做比较。
    其中P越大,产生的编码越“随机”,但是请确保P*MAX小于Long.MAX_VALUE,且一定是素数。素数表可以去这里
      

  9.   

    最初的20个号码:WW389
    LV0GI
    AUXNR
    ZSUV0
    ORR3A
    DQOBJ
    2PLJS
    RNIR1
    GMFZA
    5LC7K
    UJ9FT
    JI6N2
    8H3VB
    XF03L
    MEXAU
    BDUI3
    0CRQC
    PAOYL
    E9L6V
    38IE4
      

  10.   

    Set s = new HashSet();
    for (int i = 0; s.size() < 1000; i++) {
        s.add(随机的号码);
    }这样可以生成1000个不重复的
      

  11.   

    最多准备支持多少张券?如前面回复
    够不够用?够用的话: 
      /** 最大值 */
      public static final long MAX = 60466176; // 36 ^ 6  /** 乘法用的素数 */
      public static final long P = 15485857;
      
      /** 加法用的素数 */
      public static final long Q = 9007;  /** 编码长度 */
      public static final int LEN = 5;  /** 采用36进制 */
      public static final int RADIX = 36;  /**
       * 编码方法。
       * 
       * @param number
       *          序号
       * @return 5位编码
       * @throws IllegalArgumentException
       *           如果序号超过范围
       */
      public static String encode(int number) {
        if (number <= 0 || number > MAX) {
          throw new IllegalArgumentException();
        }
        long x = ((long) number * P + Q) % MAX;
        char[] codes = new char[LEN];
        Arrays.fill(codes, '0');
        String str = Long.toString(x, RADIX);
        System.arraycopy(str.toCharArray(),
                         0,
                         codes,
                         LEN - str.length(),
                         str.length());
        reverse(codes);
        return new String(codes).toUpperCase();
      }  private static void reverse(char[] codes) {
        for (int i = LEN >> 1; i-- > 0;) {
          codes[i] ^= codes[LEN - i - 1];
          codes[LEN - i - 1] ^= codes[i];
          codes[i] ^= codes[LEN - i - 1];
        }
      }此过程,“理论上”可逆,但是decode算法实际上没法用——太慢,几乎等同于把所有可能的值再去encode一遍做比较。
    其中P越大,产生的编码越“随机”,但是请确保P*MAX小于Long.MAX_VALUE,且一定是素数。素数表可以去这里
    不好意思?现在券号生成规则变了,只需要8位随机码就可以了,要求每个字符在生成的8位码里不重复出现