Как сохранить массив в mysql?

Есть ли способ сохранить массив в поле MySQL? Я создаю систему оценки комментариев, поэтому я хочу хранить массивы пользовательских идентификаторов, чтобы предотвратить множественные голосования. Я собираюсь создать новую таблицу, которая содержит идентификатор комментария и массив идентификаторов пользователей, которые проголосовали за этот комментарий. Затем я' Присоединюсь к таблице комментариев и этой таблице и проверим, существует ли текущий идентификатор пользователя в массиве или примечании избирателей. Если это так, значки голосования будут отключены. Я думаю, что я не позволю использовать MySQL запрос в цикле таким образом.

Вы знаете какие-нибудь лучшие способы?

47
задан April 2 June 2015 в 15:29
поделиться

6 ответов

Вы всегда можете сериализовать массив и сохранить его в базе данных.
PHP Serialize

Затем вы можете десериализовать массив, когда это необходимо.

50
ответ дан 26 November 2019 в 19:19
поделиться

Рассмотрите возможность нормализации структуры таблицы в комментариях и отдельной таблице голосов.

Таблица «комментарии»:

id
comment
user
...

Таблица «голосов»:

user_id  
comment_id
vote (downvote/upvote)

это позволит неограниченное количество голосов без необходимости иметь дело с пределами поля базы данных.

Кроме того, в будущем вам могут потребоваться такие операции, как «показать все голоса, отданные пользователем», удаление определенных голосов или ограничение максимального количества голосов в день. Эти операции невероятно легко и быстро реализовать с нормализованной структурой и ужасно медленными и сложными в сериализованном массиве.

13
ответ дан 26 November 2019 в 19:19
поделиться

у вас должно быть три таблицы: пользователи, комментарии и comment_users.

comment_users имеет всего два поля: fk_user_id и fk_comment_id

Таким образом вы можете поддерживать максимальную производительность :)

4
ответ дан 26 November 2019 в 19:19
поделиться

Я бы предпочел больше нормализовать структуру вашей таблицы, например:

COMMENTS
-------
id (pk)
title
comment
userId


USERS
-----
id (pk)
name
email


COMMENT_VOTE
------------
commentId (pk)
userId (pk)
rating (float)

Теперь это проще поддерживать! А MySQL принимает только один голос за пользователя и комментарий.

4
ответ дан 26 November 2019 в 19:19
поделиться

создать такую ​​таблицу,

CommentId    UserId
---------------------
   1            usr1
   1            usr2

Таким образом вы можете проверить, не являются ли опубликованные пользователем комментарии .. Кроме этого, должны быть таблицы для комментариев и пользователей с соответствующими идентификаторами

1
ответ дан 26 November 2019 в 19:19
поделиться

Вы можете решить эту проблему следующим образом:

CREATE TABLE comments (
    comment_id int, 
    body varchar(100), 
    PRIMARY KEY (comment_id)
);

CREATE TABLE users (
    user_id int, 
    username varchar(20), 
    PRIMARY KEY (user_id)
);

CREATE TABLE comments_votes (
    comment_id int, 
    user_id int, 
    vote_type int, 
    PRIMARY KEY (comment_id, user_id)
);

Составной первичный ключ (comment_id, user_id) в таблице пересечений comments_votes не позволит пользователям голосовать несколько раз за одни и те же комментарии.

Давайте вставим некоторые данные в приведенную выше схему:

INSERT INTO comments VALUES (1, 'first comment');
INSERT INTO comments VALUES (2, 'second comment');
INSERT INTO comments VALUES (3, 'third comment');

INSERT INTO users VALUES (1, 'user_a');
INSERT INTO users VALUES (2, 'user_b');
INSERT INTO users VALUES (3, 'user_c');

Теперь добавим несколько голосов для пользователя 1:

INSERT INTO comments_votes VALUES (1, 1, 1);
INSERT INTO comments_votes VALUES (2, 1, 1);

Вышеприведенное означает, что пользователь 1 отдал голос типа 1 за комментарии 1 и 2.

Если тот же пользователь попытается проголосовать снова за один из этих комментариев, база данных отклонит его:

INSERT INTO comments_votes VALUES (1, 1, 1);
ERROR 1062 (23000): Duplicate entry '1-1' for key 'PRIMARY'

Если вы будете использовать механизм хранения InnoDB, будет разумно также использовать foreign key ограничения на поля comment_id и user_id таблицы пересечений. Однако обратите внимание, что MyISAM, механизм хранения по умолчанию в MySQL, не применяет ограничения внешних ключей:

CREATE TABLE comments (
    comment_id int, 
    body varchar(100), 
    PRIMARY KEY (comment_id)
) ENGINE=INNODB;

CREATE TABLE users (
    user_id int, 
    username varchar(20), 
    PRIMARY KEY (user_id)
) ENGINE=INNODB;

CREATE TABLE comments_votes (
    comment_id int, 
    user_id int, 
    vote_type int, 
    PRIMARY KEY (comment_id, user_id),
    FOREIGN KEY (comment_id) REFERENCES comments (comment_id),
    FOREIGN KEY (user_id) REFERENCES users (user_id)
) ENGINE=INNODB;

Эти внешние ключи гарантируют, что строка в comments_votes никогда не будет иметь comment_id или user_id значения, не существующего в comments и users таблицах, соответственно. Внешние ключи не обязательны для создания работающей реляционной базы данных, но они определенно необходимы, чтобы избежать разрыва связей и бесхозных строк (т.е. ссылочной целостности).

На самом деле, ссылочная целостность - это то, что было бы очень трудно обеспечить, если бы вы хранили сериализованные массивы в одном поле базы данных.

62
ответ дан 26 November 2019 в 19:19
поделиться
Другие вопросы по тегам:

Похожие вопросы: