Home  >  Article  >  Backend Development  >  Summary of methods for generating unique numeric IDs in php_php tips

Summary of methods for generating unique numeric IDs in php_php tips

WBOY
WBOYOriginal
2016-05-16 20:04:231431browse

Regarding the problem of generating a unique digital ID, do you need to use rand to generate a random number, and then query the database to see if there is such a number? This seems a bit time-consuming. Is there any other way?

Of course not, there are actually two ways to solve it.

1. If you only use PHP and not a database, then the timestamp random number is the best method and it does not repeat;

2. If you need to use a database, you also need to associate some other data with this ID. Then give the id of the table in the MySQL database an AUTO_INCREMENT (auto-increment) attribute. Each time a piece of data is inserted, the id automatically increases to 1, and then uses mysql_insert_id() or LAST_INSERT_ID() to return the auto-incremented id.

Of course, there is already a ready-made solution to this problem. Using the php uuid extension can perfectly solve this problem. This extension can generate a unique complete digital signature. .

If you don’t use composer, please refer to https://github.com/lootils/uuid,

If your project is based on composer, please refer to https://github.com/ramsey/uuid

I won’t move the specific source code, friends can just take it down and use it directly

PHP generated unique identifier code example:

< &#63; 
//生成唯一标识符  
//sha1()函数, "安全散列算法(SHA1)"  
function create_unique() {  
$data = $_SERVER['HTTP_USER_AGENT'] . $_SERVER['REMOTE_ADDR']  
.time() . rand();  
return sha1($data);  
//return md5(time().$data);  
//return $data;  
} 
&#63;> 

PHP generates unique identifier function description and examples

< &#63;  
$newhash = create_unique();  
echo $newhash;  
&#63;>

Let me share one more with you

/*
 * 信号量(Semaphore)。
 * 这是一个包装类,用于解决不同平台下对“信号量”的不同实现方式。
 * 目前这个类只是象征性的,在 Windows 平台下实际是空跑(并没有真的实现互斥)。
 */
class SemWrapper
{
  private $hasSemSupport;
  private $sem;
  const SEM_KEY = 1;

  public function __construct()
  {
    $this->hasSemSupport = function_exists( 'sem_get' );
    if ( $this->hasSemSupport ) {
      $this->sem = sem_get( self::SEM_KEY );
    }
  }

  public function acquire() {
    if ( $this->hasSemSupport ) {
      return sem_acquire( $this->sem );
    }
    return true;
  }

  public function release() {
    if ( $this->hasSemSupport ) {
      return sem_release( $this->sem );
    }
    return true;
  }
}

/*
 * 顺序号发生器。
 */
class SeqGenerator
{
  const SHM_KEY = 1;

  /**
   * 对顺序号发生器进行初始化。
   * 仅在服务器启动后的第一次调用有效,此后再调用此方法没有实际作用。
   * @param int $start 产生顺序号的起始值。
   * @return boolean 返回 true 表示成功。
   */
  static public function init( $start = 1 )
  {
    // 通过信号量实现互斥,避免对共享内存的访问冲突
    $sw = new SemWrapper;
    if ( ! $sw->acquire() ) {
      return false;
    }

    // 打开共享内存
    $shm_id = shmop_open( self::SHM_KEY, 'n', 0644, 4 );
    if ( empty($shm_id) ) {
      // 因使用了 'n' 模式,如果无法打开共享内存,可以认为该共享内存已经创建,无需再次初始化
      $sw->release();
      return true;
    }

    // 在共享内存中写入初始值
    $size = shmop_write( $shm_id, pack( 'L', $start ), 0 );
    if ( $size != 4 ) {
      shmop_close( $shm_id );
      $sw->release();
      return false;
    }

    // 关闭共享内存,释放信号量
    shmop_close( $shm_id );
    $sw->release();
    return true;
  }

  /**
   * 产生下一个顺序号。
   * @return int 产生的顺序号
   */
  static public function next()
  {
    // 通过信号量实现互斥,避免对共享内存的访问冲突
    $sw = new SemWrapper;
    if ( ! $sw->acquire() ) {
      return 0;
    }

    // 打开共享内存
    $shm_id = shmop_open( self::SHM_KEY, 'w', 0, 0 );
    if ( empty($shm_id) ) {
      $sw->release();
      return 0;
    }

    // 从共享内存中读出顺序号
    $data = shmop_read( $shm_id, 0, 4 );
    if ( empty($data) ) {
      $sw->release();
      return 0;
    }

    $arr = unpack( 'L', $data );
    $seq = $arr[1];

    // 把下一个顺序号写入共享内存
    $size = shmop_write( $shm_id, pack( 'L', $seq + 1 ), 0 );
    if ( $size != 4 ) {
      $sw->release();
      return 0;
    }

    // 关闭共享内存,释放信号量
    shmop_close( $shm_id );
    $sw->release();
    return $seq;
  }
}

$a = SeqGenerator::init( time() );
var_dump($a);

for ( $i=0; $i < 10; $i++ ) {
  $seq = SeqGenerator::next();
  var_dump($seq);
}

Okay, let’s stop here today, I hope it will be helpful to everyone learning PHP

Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn