<?php
class Str
{
public static $snakeCache = [];
public static function snake($value, $delimiter = '_')
{
$key = $value;
if (isset(static::$snakeCache[$key][$delimiter])) {
return static::$snakeCache[$key][$delimiter];
}
if (! ctype_lower($value)) {
$value = preg_replace('/\s+/u', '', ucwords($value));
$value = static::lower(preg_replace('/(.)(?=[A-Z])/u', '$1'.$delimiter, $value));
}
return static::$snakeCache[$key][$delimiter] = $value;
}
/**
* Convert the given string to lower-case.
*
* @param string $value
* @return string
*/
public static function lower($value)
{
return mb_strtolower($value, 'UTF-8');
}
}
// AaBbCc1, AaBbCc2, AaBbCc3, AaBbCc4,... と接頭辞が同じ文字列を1e5個用意します
// この接頭辞付きの文字列群をスネークケースにすることを考えます
$prefix = 'AaBbCc';
$strList = array_map(fn ($i) => $prefix.$i, range(1, 1e4));
$s = microtime(true);
foreach ($strList as $str) {
// 全てを直に変更するとキャッシュが使えないため処理が遅くなります
// \Str::snake($str);
// 変換したい共通部である接頭辞を分離して、そこだけ変換にかけます。
// するとキャッシュが有効になり高速化します。
// ついでに巨大なキャッシュ配列が生成されることもなくなり、メモリにも優しいです。
[$prefix, $idx] = str_split($str, 6);
\Str::snake($prefix).$idx;
}
echo microtime(true) - $s;
preferences:
22.3 ms | 411 KiB | 5 Q