一、QT隨機數簡介
QT是一個跨平台的C++開發框架,其中包含了很多有用的類、函數庫,其中包含了產生隨機數的函數。
QRandomGenerator::global()->generate();
這個函數會返回一個無符號的隨機數,並且可以設定隨機數的範圍,如下:
QRandomGenerator::global()->bounded(10); // 返回一個0~9之間的數 QRandomGenerator::global()->bounded(1, 11); // 返回一個1~10之間的數
二、隨機數發生器的初始化
在使用隨機數發生器前,需要進行初始化操作,一般使用設備存儲的熵來進行初始化,如下:
QRandomGenerator randGen(QDateTime::currentMSecsSinceEpoch() ^ static_cast<quint64>(reinterpret_cast<quintptr>(QThread::currentThread()))); randGen.generate();
這裡使用了系統時間和當前線程的地址進行異或操作,確保初始化的唯一性。
三、隨機數應用場景舉例
1、遊戲開發
遊戲開發中經常需要用到隨機數,如隨機生成地形、怪物屬性、物品掉落等等。
// 隨機生成怪物血量 int maxHP = 1000; int minHP = 500; int randHP = randGen.bounded(minHP, maxHP+1); Monster monster(randHP);
2、密碼學
密碼學中需要用到隨機數來確保密碼的安全性,如RSA演算法中產生密鑰需要用到隨機數。
// 產生一個1024位的隨機素數 QCryptographicHash hash(QCryptographicHash::Sha3_512); while (true) { qint64 num = QRandomGenerator::global()->bounded(1e16, 1e17); hash.addData(QByteArray::number(num)); QByteArray bytes = hash.result().left(128); BIGNUM* prime = BN_bin2bn((const unsigned char*)bytes.constData(), bytes.size(), NULL); if (BN_is_prime(prime, BN_prime_checks, NULL, NULL, NULL, NULL)) { BIGNUM* zero = BN_new(); BN_zero(zero); RSA* rsa = RSA_new(); rsa->n = prime; BIGNUM* e = BN_new(); BN_set_word(e, RSA_F4); rsa->e = e; rsa->d = BN_mod_inverse(NULL, e, rsa->n, NULL); rsa->p = zero; rsa->q = zero; rsa->dmp1 = zero; rsa->dmq1 = zero; rsa->iqmp = zero; break; } }
3、數據加密
數據加密中經常需要用到隨機數生成初始化向量(IV),用來確保加密的安全性。
// AES加密 QByteArray key; QByteArray iv = RandGen.generate(16); QByteArray cipher = QCryptographicHash::hash(rawData, QCryptographicHash::Md5).toHex(); QAESEncryption crypto(QAESEncryption::AES_256, QAESEncryption::ECB); QByteArray encrypted = crypto.encode(rawData, key, iv);
4、畫圖應用
畫圖應用中也需要用到隨機數,如隨機生成各種圖形。
// 隨機生成一些點 QPainter painter(&image); for (int i = 0; i < 1000; ++i) { int x = randGen.bounded(0, image.width()); int y = randGen.bounded(0, image.height()); painter.drawEllipse(x, y, 1, 1); }
四、注意事項
使用隨機數時需要注意一些事項,如唯一性、安全性等等。
1、唯一性
在某些應用場景下,需要確保產生的隨機數唯一,如生成訂單號、用戶ID等等。
// 隨機生成一個唯一的ID quint64 randID = QDateTime::currentMSecsSinceEpoch() ^ static_cast<quint64>(reinterpret_cast<quintptr>(QThread::currentThread()));
2、安全性
在密碼學、數據加密等領域使用隨機數時需要注意安全性問題,需要使用高質量的隨機數發生器,如硬體隨機數發生器。
// 使用硬體隨機數發生器 QByteArray data; if (QRandomGenerator::securelySeeded()) { data.resize(16); if (RAND_bytes((unsigned char*)data.constData(), data.size()) != 1) { qWarning() << "RAND_bytes failed"; } }
3、分布
隨機數發生器產生的數不一定符合某些分布,如正態分布、均勻分布等等,需要進行轉換處理。
// 產生正態分布隨機數 double mean = 10.0; double stddev = 2.0; double randNum = mean + NormRand()*stddev;
五、總結
QT提供了一系列有用的隨機數發生器,可以應用到各種領域,同時需要注意隨機數的唯一性、安全性和分布問題。
原創文章,作者:小藍,如若轉載,請註明出處:https://www.506064.com/zh-tw/n/187581.html