21,882
社区成员
发帖
与我相关
我的任务
分享
class Idwork
{
const debug = 1;
static $workerId;
static $twepoch = 1361775855078;
static $sequence = 0;
const workerIdBits = 4;
static $maxWorkerId = 15;
const sequenceBits = 10;
static $workerIdShift = 10;
static $timestampLeftShift = 14;
static $sequenceMask = 1023;
private static $lastTimestamp = -1;
public function __construct($workId)
{
if ($workId > self::$maxWorkerId || $workId < 0) {
throw new Exception('worker Id can\'t be greater than 15 or less than 0');
}
self::$workerId = $workId;
}
public function timeGen()
{
//获得当前时间戳
$time = explode(' ', microtime());
$time2 = substr($time[0], 2, 3);
$timestramp = $time[1] . $time2;
return $time[1] . $time2;
}
public function tilNextMillis($lastTimestamp)
{
$timestamp = $this->timeGen();
while ($timestamp <= $lastTimestamp) {
$timestamp = $this->timeGen();
}
return $timestamp;
}
public function nextId()
{
$timestamp = $this->timeGen();//1452043798718
if (self::$lastTimestamp == $timestamp) {
self::$sequence = self::$sequence + 1 & self::$sequenceMask;
if (self::$sequence == 0) {
$timestamp = $this->tilNextMillis(self::$lastTimestamp);
}
} else {
self::$sequence = 0;
}
if ($timestamp < self::$lastTimestamp) {
throw new Excwption('Clock moved backwards. Refusing to generate id for ' . (self::$lastTimestamp - $timestamp) . ' milliseconds');
}
self::$lastTimestamp = $timestamp;
$nextId = sprintf('%.0f', $timestamp) - sprintf('%.0f', self::$twepoch) | self::$workerId << self::$workerIdShift | self::$sequence;
return $nextId;
}
}
$Idwork = new Idwork(1);
$a = $Idwork->nextId();
function get_order_sn()
{
mt_srand((double) microtime() * 1000000);
return date('Ymd') . str_pad(mt_rand(1, 99999), 4, '0', STR_PAD_LEFT);
}
echo get_order_sn();
20160106121114534741718748
20160106121114534741718783
20160106121114534741718783
20160106121114534741718719
20160106121114534741718730
20160106121114534741718777
20160106121114534741718713
20160106121114534741718782
$mch = curl_multi_init();
for($i=0; $i<4; $i++) {
$ch = curl_init('http://localhost/Idwork.php');
curl_multi_add_handle($mch, $ch);
}
$running = NULL;
do {
usleep ( 10000 );
curl_multi_exec ( $mch, $running );
} while ( $running > 0 );
80150058
80150059
80150058
80150059
80150058
80150059
80150058
80150059
80150058
80150059
80150058
80150059
80150058
80150059
显然是不能通过并发测试的echo uniqid(), PHP_EOL;
echo uniqid(), PHP_EOL;
568c83e69c671
568c83e69c671
function get_order_sn()
{
mt_srand((double) microtime() * 1000000);
return date('Ymd') . str_pad(mt_rand(1, 99999), 4, '0', STR_PAD_LEFT);
}
echo get_order_sn(), PHP_EOL;
echo get_order_sn(), PHP_EOL;
201601063753
201601063753
显然都不能通过本身的测试
$Idwork = new Idwork(1);
echo $Idwork->nextId(), PHP_EOL;
echo $Idwork->nextId(), PHP_EOL;
$test = new Idwork(1);
echo $test->nextId(), PHP_EOL;
echo $test->nextId(), PHP_EOL;
可以通过本身的测试
但并发的时候呢?
echo uniqid(), PHP_EOL;
echo uniqid(), PHP_EOL;
function get_order_sn()
{
mt_srand((double) microtime() * 1000000);
return date('Ymd') . str_pad(mt_rand(1, 99999), 4, '0', STR_PAD_LEFT);
}
echo get_order_sn(), PHP_EOL;
echo get_order_sn(), PHP_EOL;
这两种生成的方式 本身无法测试通过 是通过什么方式测试的 是指循环输出吗?