我正在研究一个使用PHP / MYSQL作为IOS应用程序后端的项目,该应用程序大量使用字典和包含文本或字符串的数组。
我需要将此文本存储在MYSQL中(来自电话中的srtrings数组),然后查询以查看文本包含(不区分大小写)所涉及的单词或短语。
例如,如果数组由{Ford,Chevy,Toyota,BMW,Buick}组成,我可能要查询它以查看其中是否包含Saab。
我知道在字段中存储数组不是MYSQL友好的,因为它会阻止优化。但是,为用户创建的这些单词集合创建单个表可能太复杂了。
因此,我正在寻找一种合理的存储方式,可能用空格或逗号分隔,以便进行合理有效的搜索。
如果它们之间用空格分开存储,我想您可以使用正则表达式执行以下操作:
SELECT
*
FROM
`wordgroups`
WHERE
wordgroup regexp '(^|[[:space:]])BLA([[:space:]]|$)';
但这看起来很时髦。
有更好的方法吗?感谢您的见识
答案 0 :(得分:1)
考虑使用FULLTEXT
索引。并使用MATCH(...) AGAINST(... IN NATURAL LANGUAGE MODE)
。
FULLTEXT
对于“单词”非常快,IN NATURAL MODE
可以解决您的Saab
示例。
答案 1 :(得分:0)
使用正则表达式可以实现您想要的,但是,由于它不能依赖任何索引,因此查询效率很低。
如果要存储单词列表并且它们在数组中的位置无关紧要,则可以考虑将它们存储在单个字段中,并用空格分隔。但是,不要使用正则表达式,而使用fulltext indexing and searching。与使用regexp进行搜索相比,此方法具有明显的优势:它使用索引。它也有一些缺点:有一个停用词列表(这些词被排除在搜索范围之外),并且还有一个最小的词长。好消息是这些参数是可配置的。此外,您还会遇到将数据存储在定界字段中的所有弊端,如SO Is storing a delimited list in a database column really that bad?问题中所述。
但是,如果要使用字典(键-值对)或列表中的位置可能很重要,则上述数据结构将无效。
在这种情况下,我会考虑是否mysql是首先存储数据的正确选择。如果您有多维列表或包含列表的列表,那么我肯定会选择其他nosql解决方案。
如果只需要简单的二维列表/词典,则可以将它们全部存储在具有类似以下结构的单个表中:
list_id - unique identifier of the list, primary key
user_id - id of the user the list belongs to
key - for dictionaries this is the lookup field (indexed), for other lists it may store the position of the element. String data type.
value - the field holding the value (indexed). Data type should be string, so that it could hold different data types as well.
使用键或值字段上的索引,可以快速,高效地查找列表是否包含某个值。