2015-07-11 4 views
0

G'dayHacklang - Поиск по карте

В строгом режиме есть ли способ поиска Карты по значению, а не по ключу?

Скажем, у меня есть карта:

$temp = Map{'melon', 'apple'}; 

Как я мог искать по значению?

ответ

1

Во-первых, карта в вашем примере не является действительной картой. Карты в Hack представляют собой пары ключ-значение, и вы предоставляете только ключи. Я предполагаю, что это опечатка, и пример вы имели в виду, чтобы дать что-то вроде

$temp = Map {'fruit' => 'apple', 'veg' => 'carrot'}; 

Для поиска карты в Hack, вы можете сделать то же самое, если бы в PHP: итерацию над ней в О (п) сканирования. Вот примерная функция, которая делает это, написанная с помощью генераторов Hack, поэтому она будет иметь правильный тип независимо от входной карты.

function find_key<Tk, Tv>(Map<Tk, Tv> $haystack, Tv $needle): ?Tk { 
    foreach ($haystack as $k => $v) { 
    if ($v === $needle) { 
     return $k; 
    } 
    } 
    return null; 
} 

Однако последний вопрос к вам: почему вы ищете такую ​​карту? Карты предназначались для быстрого поиска значений для данного ключа, а также быстрой итерации по всем парам ключ/значение. Это не, предназначенные для поиска значений, как это - поэтому он принимает цикл O (n), который должен содержать предупреждающие знаки о том, что то, что вы делаете, может быть не лучшим. Возможно, вам захочется рассмотреть возможность использования более подходящей структуры данных: возможно, создание обратной карты, если вы часто выполняете эту операцию, или с помощью набора или вектора в зависимости.

+0

Я читал документы, и они сказали использовать Карты как можно больше. Я не знал, что Maps требует пары ключ-значение. Я предположил, что они добавят элемент в конец объекта, похожий на то, как массивы работают в php. Второй вопрос, почему. У меня есть несколько массивов, которые предназначены для поиска по значению, и если значение существует в одном из этих массивов, оно предназначено для возврата константы. Я предположил, что, возможно, у Карты была функция типа «содержать», но поиск по значению не является ключевым. – Tim

+1

Карты очень преднамеренно не ведут себя как массивы PHP, чтобы избежать путаницы того, что именно подразумевает семантика, что вы видите много в массивах PHP - поведение «array_merge» иллюстрирует эту сложность. Вот почему есть «Вектор» и «Набор», который в зависимости от того, почему ваша карта «спроектирована для поиска по значению», может стать лучшей заменой. Поиск карты по значению почти никогда не является хорошей идеей и свидетельствует о плохом дизайне. Можете ли вы связать меня со страницей документов, в которой говорится, что всегда используйте карту, мы должны ее исправить/уточнить. –

+0

Я неправильно понял информацию, http://docs.hhvm.com/manual/en/hack.arrays.php - Говорит: Руководство по языку Hack - это использование коллекций всякий раз, когда это возможно. Извиняюсь. Я принял то, что было сказано вне контекста. Я буду использовать «Sets», поскольку они кажутся тем, что я хотел бы использовать. – Tim