[php] PHP에 Java HashMap에 해당하는 것이 있습니까?
Java의 HashMap과 유사한 PHP 개체가 필요하지만 Google에서 찾지 못했기 때문에 누군가가 PHP에서 HashMaps를 모방하는 방법을 알고 있다면 도움을 주시면 감사하겠습니다.
답변
PHP의 배열은 키 값 구조를 가질 수 있습니다.
답변
원하는 것에 따라 SPL Object Storage 클래스에 관심이있을 수 있습니다.
http://php.net/manual/en/class.splobjectstorage.php
객체를 키로 사용할 수 있고, 계산할 인터페이스가 있고, 해시 및 기타 장점을 얻을 수 있습니다.
$s = new SplObjectStorage;
$o1 = new stdClass;
$o2 = new stdClass;
$o2->foo = 'bar';
$s[$o1] = 'baz';
$s[$o2] = 'bingo';
echo $s[$o1]; // 'baz'
echo $s[$o2]; // 'bingo'
답변
O (1) 읽기 복잡성으로 PHP에서 HashMap과 같은 Java를 만듭니다.
phpsh 터미널을 엽니 다.
php> $myhashmap = array();
php> $myhashmap['mykey1'] = 'myvalue1';
php> $myhashmap['mykey2'] = 'myvalue2';
php> echo $myhashmap['mykey2'];
myvalue2
$myhashmap['mykey2']
이 경우 의 복잡도는 일정한 시간 O (1)으로 보입니다. 즉, $ myhasmap의 크기가 무한대에 가까워 질 때 키가 주어진 값을 검색하는 데 걸리는 시간은 동일하게 유지됩니다.
읽은 PHP 배열이 일정한 시간이라는 증거 :
PHP 인터프리터를 통해 실행하십시오.
php> for($x = 0; $x < 1000000000; $x++){
... $myhashmap[$x] = $x . " derp";
... }
루프는 10 억 개의 키 / 값을 추가하며, 메모리를 모두 소모 할 수있는 해시 맵에 모두 추가하는 데 약 2 분이 걸립니다.
그런 다음 조회하는 데 걸리는 시간을 확인하세요.
php> system('date +%N');echo " " . $myhashmap[10333] . " ";system('date +%N');
786946389 10333 derp 789008364
그렇다면 PHP 배열 맵 조회는 얼마나 빠릅니까?
은 10333
우리가 고개 열쇠입니다. 1 백만 나노초 == 1 밀리 초. 키에서 값을 가져 오는 데 걸리는 시간은 206 만 나노초 또는 약 2 밀리 초입니다. 배열이 비어있는 경우 거의 같은 시간입니다. 이것은 나에게 일정한 시간처럼 보입니다.
답변
$fruits = array (
"fruits" => array("a" => "Orange", "b" => "Banana", "c" => "Apple"),
"numbers" => array(1, 2, 3, 4, 5, 6),
"holes" => array("first", 5 => "second", "third")
);
echo $fruits["fruits"]["b"]
‘바나나’출력
답변
O (1) 읽기 복잡성 (자신의 해시 함수의 품질에 따라 다름)이있는 문자열 및 정수 이외의 키로도 작동하는 HashMap.
간단한 hashMap을 직접 만들 수 있습니다. hashMap이하는 일은 해시를 인덱스 / 키로 사용하여 배열에 항목을 저장하는 것입니다. 해시 함수는 가끔 충돌을 제공하므로 (자주하지는 않지만 발생할 수 있음) hashMap의 항목에 대해 여러 항목을 저장해야합니다. 그 간단한 것은 hashMap입니다.
class IEqualityComparer {
public function equals($x, $y) {
throw new Exception("Not implemented!");
}
public function getHashCode($obj) {
throw new Exception("Not implemented!");
}
}
class HashMap {
private $map = array();
private $comparer;
public function __construct(IEqualityComparer $keyComparer) {
$this->comparer = $keyComparer;
}
public function has($key) {
$hash = $this->comparer->getHashCode($key);
if (!isset($this->map[$hash])) {
return false;
}
foreach ($this->map[$hash] as $item) {
if ($this->comparer->equals($item['key'], $key)) {
return true;
}
}
return false;
}
public function get($key) {
$hash = $this->comparer->getHashCode($key);
if (!isset($this->map[$hash])) {
return false;
}
foreach ($this->map[$hash] as $item) {
if ($this->comparer->equals($item['key'], $key)) {
return $item['value'];
}
}
return false;
}
public function del($key) {
$hash = $this->comparer->getHashCode($key);
if (!isset($this->map[$hash])) {
return false;
}
foreach ($this->map[$hash] as $index => $item) {
if ($this->comparer->equals($item['key'], $key)) {
unset($this->map[$hash][$index]);
if (count($this->map[$hash]) == 0)
unset($this->map[$hash]);
return true;
}
}
return false;
}
public function put($key, $value) {
$hash = $this->comparer->getHashCode($key);
if (!isset($this->map[$hash])) {
$this->map[$hash] = array();
}
$newItem = array('key' => $key, 'value' => $value);
foreach ($this->map[$hash] as $index => $item) {
if ($this->comparer->equals($item['key'], $key)) {
$this->map[$hash][$index] = $newItem;
return;
}
}
$this->map[$hash][] = $newItem;
}
}
그것이 작동하려면 키에 대한 해시 함수와 동등성을위한 비교자가 필요합니다 (항목이 몇 개만 있거나 다른 이유로 속도가 필요하지 않은 경우 해시 함수가 0을 반환하도록 할 수 있습니다. 모든 항목은 동일한 버킷에 넣으면 O (N) 복잡성이 발생합니다)
다음은 그 예입니다.
class IntArrayComparer extends IEqualityComparer {
public function equals($x, $y) {
if (count($x) !== count($y))
return false;
foreach ($x as $key => $value) {
if (!isset($y[$key]) || $y[$key] !== $value)
return false;
}
return true;
}
public function getHashCode($obj) {
$hash = 0;
foreach ($obj as $key => $value)
$hash ^= $key ^ $value;
return $hash;
}
}
$hashmap = new HashMap(new IntArrayComparer());
for ($i = 0; $i < 10; $i++) {
for ($j = 0; $j < 10; $j++) {
$hashmap->put(array($i, $j), $i * 10 + $j);
}
}
echo $hashmap->get(array(3, 7)) . "<br/>";
echo $hashmap->get(array(5, 1)) . "<br/>";
echo ($hashmap->has(array(8, 4))? 'true': 'false') . "<br/>";
echo ($hashmap->has(array(-1, 9))? 'true': 'false') . "<br/>";
echo ($hashmap->has(array(6))? 'true': 'false') . "<br/>";
echo ($hashmap->has(array(1, 2, 3))? 'true': 'false') . "<br/>";
$hashmap->del(array(8, 4));
echo ($hashmap->has(array(8, 4))? 'true': 'false') . "<br/>";
출력으로 제공됩니다.
37
51
true
false
false
false
false
답변
php에서 사용자 정의 HashMap 클래스를 만들 수 있습니다. get 및 set과 같은 기본 HashMap 속성을 포함하는 아래 표시된 예제.
class HashMap{
public $arr;
function init() {
function populate() {
return null;
}
// change to 999 for efficiency
$this->arr = array_map('populate', range(0, 9));
return $this->arr;
}
function get_hash($key) {
$hash = 0;
for ($i=0; $i < strlen($key) ; $i++) {
$hash += ord($key[$i]);
}
// arr index starts from 0
$hash_idx = $hash % (count($this->arr) - 1);
return $hash_idx;
}
function add($key, $value) {
$idx = $this->get_hash($key);
if ($this->arr[$idx] == null) {
$this->arr[$idx] = [$value];
} else{
$found = false;
$content = $this->arr[$idx];
$content_idx = 0;
foreach ($content as $item) {
// checking if they have same number of streams
if ($item == $value) {
$content[$content_idx] = [$value];
$found = true;
break;
}
$content_idx++;
}
if (!$found) {
// $value is already an array
array_push($content, $value);
// updating the array
$this->arr[$idx] = $content;
}
}
return $this->arr;
}
function get($key) {
$idx = $this->get_hash($key);
$content = $this->arr[$idx];
foreach ($content as $item) {
if ($item[1] == $key) {
return $item;
break;
}
}
}
}
이것이 도움이 되었기를 바랍니다.