>  기사  >  백엔드 개발  >  PHP에서 고유 ID를 생성하는 SnowFlake 알고리즘에 대한 자세한 설명

PHP에서 고유 ID를 생성하는 SnowFlake 알고리즘에 대한 자세한 설명

墨辰丷
墨辰丷원래의
2018-05-29 15:01:401674검색

눈송이 알고리즘이란 무엇인가요? 먼저, 분산 시스템에서 고유한 ID를 생성하고 그 ID가 저절로 대략 증가하도록 유지하는 방법에 대해 질문하겠습니다. 이것이 트위터에서 가장 중요한 비즈니스 시나리오이기 때문에 트위터는 눈송이 알고리즘을 출시했습니다.

서문: 최근에 CMS 시스템을 구축해야 했고, 기능이 비교적 간단하고 요구 사항이 유연하기 때문에 WP와 같은 성숙한 시스템을 포기하고 비교적 간단한 시스템을 직접 구축했습니다. 기사 세부정보 페이지 URL을 의사 정적 URL 형식, 즉 xxx.html로 만들고 싶어 xxx에서 자동 증가 기본 키를 직접 사용하는 것을 고려했지만 이로 인해 기사 수가 노출될 수도 있다고 생각합니다. 초기값을 높게 설정할 수도 있지만 여전히 가능하다고 하는데, ID 차이를 기준으로 일정 기간 내 기사 수를 계산하므로 고유한 ID를 생성할 수 있는 알고리즘이 필요합니다.

제가 고려한 방법으로는

  1. 타임스탬프를 직접 사용하는 방법이나 그로부터 파생된 일련의 방법이 있습니다

  2. Mysql에 포함된 uuid

위 두 가지 방법을 찾을 수 있어서 이겼습니다. 많이 하지 마세요

트위터의 SnowFlake 알고리즘을 선택했습니다

이 알고리즘의 이점은 매우 간단합니다. 초당 약 400만 개의 서로 다른 16자리 ID(십진수)를 생성할 수 있습니다

원리는 매우 간단합니다.

ID는 64비트 구성으로 구성됩니다

첫 번째 비트는 비어있습니다

41bit는 밀리초 단위의 타임스탬프를 저장하는 데 사용됩니다

10bit는 머신 ID를 저장하는 데 사용됩니다

12bit는 자동 증가 ID를 저장하는 데 사용됩니다

제외 사용할 수 없는 것으로 표시된 가장 높은 비트에 대해 나머지 3개의 그룹 비트 점유는 특정 비즈니스 요구 사항에 따라 부동될 수 있습니다. 기본적으로 41비트 타임스탬프는 2082년까지 이 알고리즘의 사용을 지원할 수 있고, 10비트 작업 기계 ID는 1023개의 기계를 지원할 수 있으며 일련 번호는 4095개의 자동 증가 시퀀스 ID를 생성하는 데 1밀리초를 지원합니다.

다음은 PHP 소스 코드입니다

<?php
namespace App\Services;

abstract class Particle {
  const EPOCH = 1479533469598;
  const max12bit = 4095;
  const max41bit = 1099511627775;

  static $machineId = null;

  public static function machineId($mId = 0) {
    self::$machineId = $mId;
  }

  public static function generateParticle() {
    /*
    * Time - 42 bits
    */
    $time = floor(microtime(true) * 1000);

    /*
    * Substract custom epoch from current time
    */
    $time -= self::EPOCH;

    /*
    * Create a base and add time to it
    */
    $base = decbin(self::max41bit + $time);


    /*
    * Configured machine id - 10 bits - up to 1024 machines
    */
    if(!self::$machineId) {
      $machineid = self::$machineId;
    } else {
      $machineid = str_pad(decbin(self::$machineId), 10, "0", STR_PAD_LEFT);
    }
    
    /*
    * sequence number - 12 bits - up to 4096 random numbers per machine
    */
    $random = str_pad(decbin(mt_rand(0, self::max12bit)), 12, "0", STR_PAD_LEFT);

    /*
    * Pack
    */
    $base = $base.$machineid.$random;

    /*
    * Return unique time id no
    */
    return bindec($base);
  }

  public static function timeFromParticle($particle) {
    /*
    * Return time
    */
    return bindec(substr(decbin($particle),0,41)) - self::max41bit + self::EPOCH;
  }
}

?>

호출 방법은 다음과 같습니다

Particle::generateParticle($machineId);//生成ID
Particle::timeFromParticle($particle);//反向计算时间戳

여기서 기계 ID가 0을 통과하면 10비트가 제거되는 경우가 있습니다. 아이디를 너무 많이 사용하지 못할 수도 있습니다

위 내용은 이 글의 전체 내용입니다. 모든 분들의 공부에 도움이 되었으면 좋겠습니다.


관련 추천:

phpGenerate into 고유 번호 id 방법 요약, php generate into id 요약

[php] mysql 글로벌 ID generate into 솔루션, phpmysql global id

php generate into 고유 id 자세한 설명

위 내용은 PHP에서 고유 ID를 생성하는 SnowFlake 알고리즘에 대한 자세한 설명의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

성명:
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.