#algorithm #data-structures #hash
#алгоритм #структуры данных #хэш
Вопрос:
user_1 is in [group_1, group_2]
user_2 is in [group_2, group_3]
therefore,
group_1 has members [user_1]
group_2 has members [user_1, user_2]
group_3 has members [user_2]
Вариант использования — много чтения, меньше записи, поиск:
- группы, в которых находится данный пользователь.
- члены в заданных группах.
Существует ли какая-либо правильная структура данных для этого с низким объемом памяти?
Комментарии:
1. Разве это не отношение «многие ко многим»?
2. В общем, да. Я говорю, что один ко многим — это выделение вариантов использования.
3. Пропущенные символы подчеркивания:: group_1, group_2, group_3 следует последовательно использовать выше.
4. Спасибо. он пересмотрен.
Ответ №1:
Структура данных Graph может быть лучшим вариантом для решения этой проблемы.
Подход к списку смежности:
Сопоставьте номер группы со списком номеров пользователей, с которыми связаны пользователи.
Карта <Номер группы, список пользователей>
Аналогичный случай с другим отображением.
Сопоставьте номер пользователя со списком номеров групп, с которыми связан этот пользователь.
Карта <Номер пользователя, список групп>
Ответ №2:
Вот некоторый Python, который создает класс из двух сопоставлений и как они используются.
# Initial input maps users to any iterable collection of groups e.g. a list.
u2g = {'user_1': ['group_1', 'group_2'],
'user_2': ['group_2', 'group_3'],
}
class Bi_map():
def __init__(self, u2g_in):
# internal forward map of user to tuple of groups
self.u2g = {user: tuple(groups)
for user, groups in u2g_in.items()}
# Assemble reverse mapping of group to appendable list of users
g2u = dict()
for user, groups in u2g_in.items():
for group in groups:
if group in g2u:
g2u[group].append(user)
else:
g2u[group] = [user]
# internal reverse map of group to tuple of users
self.g2u = {group: tuple(users)
for group, users in g2u.items()}
if __name__ == '__main__':
# Typical use
bi_map = Bi_map(u2g)
assert bi_map.u2g == {'user_1': ('group_1', 'group_2'),
'user_2': ('group_2', 'group_3')}
assert bi_map.g2u == {'group_1': ('user_1',),
'group_2': ('user_1', 'user_2'),
'group_3': ('user_2',)}
print(bi_map.u2g['user_2']) # outputs: ('group_2', 'group_3')
print(bi_map.g2u['group_2']) # outputs: ('user_1', 'user_2')
Теперь вышесказанное предполагает, что у вас есть начальное одностороннее сопоставление; хотите создать двустороннее сопоставление; затем прочитайте сгенерированные карты с этого момента.
Если вы хотите время от времени добавлять сопоставления nextra, то одной из модификаций было бы сохранение сопоставления строк со списками строк в классе и добавление методов для их обновления.