mysql在其他表的数组上使用filter表

8xiog9wr  于 2021-06-18  发布在  Mysql
关注(0)|答案(2)|浏览(375)

我有两张table:profile和hobbie
每个配置文件最多可以选择hobbie,profile.p\u嗜好中的安全内容作为id数组(例如:[1,5,7,8,9])
现在我想知道一个人物的名字。我想应该是链接:

SELECT hobbie.h_name
FROM profile, hobbie
WHERE profile.p_id=37 AND hobbie.h_id IN profile.p_hobbies

结果是失败#1064

1064-fehler-in-der-sql语法。bite die korrekte syntax im handbuch nachschlagen bei'profile.p\u兴趣爱好限制0,25'在zeile 3中

我已经在其他sql查询中使用了in方法。如果我想使用的数组也是来自sql数据库的数据,我想我不能使用它?
如果不使用多个查询,我能做什么?
我用的是mariadb-9

xqkwcwgp

xqkwcwgp1#

最好的选择是规范化数据。在sql中,将数集存储为逗号分隔的列表被认为是有害的。为什么有害?
它不能很好地扩展,因为它不能使用索引进行搜索
更新数字集是困难的;考虑移除的问题 21,2,3,4 . 这在sql中是一团糟。
一些sql变体支持更新函数。但扩大规模的问题仍然存在(不要对这个建议太生气:我们大多数人都曾经犯过这样或那样的数据库设计错误。)
你的个人资料和爱好之间有一种多对多的关系。因此需要一个名为 profile_hobbie 里面有两列, p_id 以及 h_id . 当一个个人资料开始做一个爱好时,你在其中插入一行 profile_hobbie 个人资料和爱好的id。如果一个档案停止做一个爱好,你就删除那一行。
那么您的查询将如下所示:

SELECT hobbie.h_name
    FROM profile
    JOIN profile_hobbie ON profile.p_id = profile_hobbie.p_id
    JOIN hobbie ON profile_hobbie.id = hobbie.h_id
   WHERE profile.p_id=37

这将产生一个(可能是空的)所选配置文件的爱好列表。
您也可以尝试使用mysql的find \u in \u set()函数,但是您可能会遇到整数和字符串之间的转换问题。

SELECT hobbie.h_name
     FROM profile
     JOIN hobbie ON (FIND_IN_SET(hobbie.h_id, profile.p_hobbies) > 0)

但是,戈登是对的。这使用了糟糕的字符串处理技巧。

bjp0bcyl

bjp0bcyl2#

这太长了,不能发表评论。
mysql中没有数组类型。您的数据结构有问题。你应该有一个关联/连接表,每个用户和爱好有一行。像这样:

create table profileHobbies (
    profileHobbieId int auto_increment primary key,
    profileId int,
    hobbieId int,
    foreign key (profileId) references profiles(profileId),
    foreign key (hobbieId) references hobbies(hobbieId)
);

行如下所示:

profileHobbieId   profileId   HobbieId
       1              1           1
       2              1           3
       3              1           5

那么您的查询将如下所示:

SELECT h.h_name
FROM profileHobbies ph JOIN
     hobbie h
     ON ph.hobbie_id = h.hobbie_id
WHERE ph.profile_id = 37 ;

您不想将爱好列表存储为分隔字符串的原因有很多。以下是一些:
ID是整数。数据应使用正确的类型存储,整数不是字符串。
应该正确声明外键关系。
sql的字符串处理能力很差。
管理列表所需的字符串函数阻止优化器使用索引。
sql有一个非常好的数据结构来存储列表。它被称为表,而不是字符串。

相关问题