如何在c#中生成优惠券代码?

Ite*_*ity 15 c#

我需要生成优惠券代码[5到10位],仅供一次使用.什么是生成和检查是否使用的最佳方法?

编辑:我更喜欢字母数字字符 - 亚马逊像礼品券代码必须是唯一的.

小智 17

在生成凭证代码时 - 您应该考虑是否具有可预测的序列是否真正符合您的要求.

例如,凭证代码:ABC101,ABC102,ABC103等是相当可预测的.用户可以很容易地猜出凭证代码.

为了防止这种情况 - 你需要一些防止随机猜测工作的方法.

两种方法:

  • 在您的优惠券代码中嵌入校验和.

    信用卡上的最后一个数字是校验和(校验位) - 当您以某种方式将其他数字相加时,可以确保有人正确输入了数字.请参阅:http://www.beachnet.com/~hstiles/cardtype.html(谷歌的第一个链接),了解如何为信用卡完成此操作.

  • 有一个很大的密钥空间,只有人口稀少.

    例如,如果要生成1,000个凭证 - 那么1,000,000的密钥空间意味着您应该能够使用随机生成(使用重复和顺序检查)来确保难以猜测另一个凭证代码.

这是一个使用大键空间方法的示例应用程序:

    static Random random = new Random();

    static void Main(string[] args)
    {
        int vouchersToGenerate = 10;
        int lengthOfVoucher = 10; 


        List<string> generatedVouchers = new List<string>();
        char[] keys = "ABCDEFGHIJKLMNOPQRSTUVWXYZ01234567890".ToCharArray();


        Console.WriteLine("Vouchers: ");
        while(generatedVouchers.Count < vouchersToGenerate)
        {
            var voucher = GenerateVoucher(keys, lengthOfVoucher); 
            if (!generatedVouchers.Contains(voucher))
            {
                generatedVouchers.Add(voucher);
                Console.WriteLine("\t[#{0}] {1}", generatedVouchers.Count, voucher);
            }
        }

        Console.WriteLine("done");

        Console.ReadLine();
    }

    private static string GenerateVoucher(char[] keys, int lengthOfVoucher)
    {
        return Enumerable
            .Range(1, lengthOfVoucher) // for(i.. ) 
            .Select(k => keys[random.Next(0, keys.Length - 1)])  // generate a new random char 
            .Aggregate("", (e, c) => e + c); // join into a string
    }
Run Code Online (Sandbox Code Playgroud)


Ton*_*ony 6

基于Will Hughes和Shekhar_Pro的答案(并且仅仅因为我发现这个问题很有趣)这里是另一个实现,但我对你的凭证代码长度的要求有点自由.

使用base 32编码器我发现你可以使用该Tick值来生成字母数字字符串.将滴答计数编码为基数32会产生13个字符的字符串,可对其进行格式化以使其更具可读性.

    public void GenerateCodes()
    {
        Random random = new Random();
        DateTime timeValue = DateTime.MinValue;
        // Create 10 codes just to see the random generation.
        for(int i=0; i<10; ++i)
        {
            int rand = random.Next(3600)+1; // add one to avoid 0 result.
            timeValue = timeValue.AddMinutes(rand);
            byte[] b = System.BitConverter.GetBytes(timeValue.Ticks);
            string voucherCode = Transcoder.Base32Encode(b);
            Console.WriteLine(string.Format("{0}-{1}-{2}", 
                              voucherCode.Substring(0,4),
                              voucherCode.Substring(4,4),
                              voucherCode.Substring(8,5)));
        }
    }
Run Code Online (Sandbox Code Playgroud)

这是输出

AARI-3RCP-AAAAA
ACOM-AAZF-AIAAA
ABIH-LV7W-AIAAA
ADPL-26FL-AMAAA
ABBL-W6LV-AQAAA
ADTP-HFIR-AYAAA
ACDG-JH5K-A4AAA
ADDE-GTST-BEAAA
AAWL-3ZNN-BIAAA
AAGK-4G3Y-BQAAA
Run Code Online (Sandbox Code Playgroud)

如果您为Random对象使用已知种子并记住已创建的代码数量,则可以继续生成代码; 例如,如果您需要更多代码并希望确定您不会生成重复项.