Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> C#

สร้างตัวเลขสุ่มใน C# ด้วย Random Class

C# ใช้ Class System.Random สำหรับ Pseudorandom Number Generation

การใช้งานพื้นฐาน

using System;

public class Program
{
    public static void Main()
    {
        Random r = new Random();

        // Random int: 0 ถึง Int32.MaxValue
        int any = r.Next();

        // Random int: 0 ถึง 99
        int zeroTo99 = r.Next(100);

        // Random int: 10 ถึง 49 (Inclusive start, Exclusive end)
        int tenTo49 = r.Next(10, 50);

        // Random double: 0.0 ถึง 1.0
        double d = r.NextDouble();

        // Random bytes
        byte[] bytes = new byte[16];
        r.NextBytes(bytes);

        Console.WriteLine($"Any: {any}");
        Console.WriteLine($"0-99: {zeroTo99}");
        Console.WriteLine($"10-49: {tenTo49}");
        Console.WriteLine($"Double: {d}");
    }
}

⚠️ ปัญหา Thread Safety & Performance

Random ไม่ใช่ Thread-Safe การ Share Instance ระหว่าง Thread จะทำให้ผลลัพธ์แย่ (Contention, Correlation)

แนะนำ: ThreadLocal หรือ Random.Shared (.NET 6+)

.NET 6+ (Recommended):
// Shared Instance - Thread-Safe
int value = Random.Shared.Next(10, 50);
double d = Random.Shared.NextDouble();

// .NET Framework / .NET Core < 6:
private static readonly ThreadLocal _localRandom =
    new ThreadLocal(() => new Random(Guid.NewGuid().GetHashCode()));

int value = _localRandom.Value.Next(10, 50);

Cryptographically Secure Random (Security Critical)

using System.Security.Cryptography;

// สำหรับ: Password, Token, Key, Salt, Nonce
using var rng = RandomNumberGenerator.Create();

byte[] bytes = new byte[32];
rng.GetBytes(bytes); // 256-bit Random

// Random Int Secure
byte[] intBytes = new byte[4];
rng.GetBytes(intBytes);
int secureInt = BitConverter.ToInt32(intBytes, 0) & 0x7FFFFFFF; // Positive Only

Seed Control (Reproducible Random)

// Same Seed = Same Sequence (Good for Testing/Debugging)
var r1 = new Random(12345);
var r2 = new Random(12345);
Console.WriteLine(r1.Next() == r2.Next()); // True

// Default Seed = Environment.TickCount (Time-based)

Random Extensions (Helper Methods)

public static class RandomExtensions
{
    public static T NextEnum(this Random r) where T : Enum
    {
        var values = Enum.GetValues(typeof(T));
        return (T)values.GetValue(r.Next(values.Length));
    }

    public static string NextString(this Random r, int length, string chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789")
    {
        return new string(Enumerable.Range(0, length).Select(_ => chars[r.Next(chars.Length)]).ToArray());
    }

    public static bool NextBool(this Random r, double probability = 0.5)
    {
        return r.NextDouble() < probability;
    }
}

// ใช้งาน
var color = Random.Shared.NextEnum();
var token = Random.Shared.NextString(16);
var lucky = Random.Shared.NextBool(0.1); // 10% chance

สรุปเลือกใช้

Use CaseClass/Method
General Purpose (Game, Sim, Test)Random.Shared (.NET 6+) / ThreadLocal<Random>
Security (Password, Token, Crypto)RandomNumberGenerator
Reproducible (Unit Test, Debug)new Random(seed)
Parallel/High ThroughputThreadLocal<Random> หรือ Random.Shared