Существует ли какое-либо представление математического набора в PHP?
Многие языки имеют структуру данных "Набор", которая обычно содержит только уникальные значения из определенной коллекции объектов. Например, если вы добавите целые числа 1, 4, 5, 1, 2, и 6 к набору, в конце концов набор фактически будет содержать только 1, 4, 5, 2 и 6.
Я не наблюдал подобной коллекции в PHP. Есть ли такая коллекция, встроенная в язык, или что-то должно быть настроено на заказ?
4 answers
Сомневаюсь, что в него что-то встроено, но добиться этого очень просто:
<?
$set = array(1, 4, 5, 1, 2, 6); // original set
$set = array_unique($set);
//$set = array_values($set); // add this to reset the keys
print_r($set); // returns 1, 4, 5, 2 and 6.
Я не заметил никакого типа коллекции "Set" на языке PHP, поэтому я запустил свой собственный метод моделирования набора. Я подхожу к набору, подобному хэш-таблице. Ключи в хэш-таблице по умолчанию принадлежат набору. Вы можете использовать это в своих интересах.
Например, предположим, что у меня есть случайно сгенерированный массив целых чисел $random_integers
. Следующее даст уникальный массив значений, содержащихся в $random_integers
:
$random = array(1,1,1,3,4,5,3,45,7);
$set = array();
foreach($random as $key => $value) {
$set[$value] = 1;
}
$set = array_keys($set);
print_r($random);
print_r($set);
array_keys
это функция, включенная в PHP. Вы можете использовать это, чтобы извлеките все ключи из вашей хэш-таблицы, которые эквивалентны набору.
Подводным камнем здесь является то, что в качестве ключей массива можно использовать только целые числа и строки. Таким образом, любые объекты, которые вы используете, будут нуждаться в некотором строковом или целочисленном представлении, если вы хотите включить их в свой набор.
Также обратите внимание, что в моем примере вам не нужно делать дополнительный шаг для извлечения ключей массива. $set
уже является набором. Вызов array_keys
просто дает вам уникальные значения, если вам понадобится их.
Подобной коллекции, которая является частью ядра PHP, не существует. Вы можете подобраться довольно близко, используя ключи массива или используя SplObjectStorage
.
В старые времена Turbo Pascal поддерживал тип НАБОРА для хранения значений до 255. Используемый механизм был довольно простым, используя массив из 32 байт, каждое значение в наборе хранилось в одном из 32*8=256 бит в этом массиве. Значение 0, сохраненное в бите 0 массива[0], значение 1, сохраненное в бите 1 массива[0].. значение 255, сохраненное в бите 7 массива[31]:
Поиск байта и бита значения:
BYTEPOS = $value >> 3 (0..7 => 0, 8..15 => 1 etc)
BITPOS = $value & 7 (0,8,16 ... => bit 0 1,9,17 => bit 1 etc)
Пустой набор [0..255];
$theSET = array( 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 );
Добавление значения:
$theSET[ $value >> 3 ] = $theSET [ $value >> 3 ] | (1 << ($value & 7));
Удаление :
$theSET[ $value >> 3 ] = $theSET [ $value >> 3 ] & ~(1 << ($value & 7));
Проверка:
inSET = ($theSET [ $value >> 3 ] & (1 << ($value & 7)) == (1 << ($value & 7));
Операции над двумя наборами могут выполняться в виде итераций,
Объединение:
$SetA[$i] = $SetA[$i] | $SetB[$i]
Только значения, отсутствующие в setB:
$SetA[$i] = $SetA[$i] & (~$SetB[$i])
Эст