Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/sql/87.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
多列索引与每列的索引?mysql_Mysql_Sql_Database_Indexing - Fatal编程技术网

多列索引与每列的索引?mysql

多列索引与每列的索引?mysql,mysql,sql,database,indexing,Mysql,Sql,Database,Indexing,我有以下表格: 业务表: bussId | nameEn | nameHe | nameAr | status | favor | cityId | categoryId categoryId | keywords userId | bussId userId | bussId | rating 类别表: bussId | nameEn | nameHe | nameAr | status | favor | cityId | categoryId categoryId | key

我有以下表格:

业务表:

bussId | nameEn | nameHe | nameAr | status | favor | cityId | categoryId 
categoryId | keywords
userId | bussId
userId | bussId | rating
类别表:

bussId | nameEn | nameHe | nameAr | status | favor | cityId | categoryId 
categoryId | keywords
userId | bussId
userId | bussId | rating
喜爱的表格:

bussId | nameEn | nameHe | nameAr | status | favor | cityId | categoryId 
categoryId | keywords
userId | bussId
userId | bussId | rating
评级表:

bussId | nameEn | nameHe | nameAr | status | favor | cityId | categoryId 
categoryId | keywords
userId | bussId
userId | bussId | rating
我正在运行这个查询,它使用cityId和搜索(business.nameEn、business.nameAr、business.nameHe、categories.keywords)过滤企业,然后按偏好、状态和名称排序

SELECT DISTINCT bussID ,businessName, bussStatus,favor, ratingCount , ratingSum 
FROM
(
     SELECT DISTINCT business.bussID , business.nameEn as businessName , bussStatus,favor,
        (SELECT COUNT(rating.bussId) FROM `rating` WHERE  rating.bussId = business.bussID) as ratingCount ,
        (SELECT SUM(rating.rating) FROM `rating` WHERE  rating.bussId = business.bussID) as ratingSum 
     FROM business LEFT JOIN favourites ON (favourites.bussID = business.bussID AND favourites.userID = '30000')
     INNER JOIN `categories` ON (`categories`.`categoryId` = `business`.`subCategoryId`  ) 
     WHERE  (bussiness.cityID = 11)
            AND (
                    ( REPLACE( REPLACE(REPLACE(LOWER(`bussiness`.`nameEn`),'أ','ا'),'أ','ا') ,'ة','ه') LIKE '%test%' )
                  OR( REPLACE( REPLACE(REPLACE(LOWER(`bussiness`.`nameHe`),'أ','ا'),'أ','ا') ,'ة','ه') LIKE '%test%' )
                  OR( REPLACE( REPLACE(REPLACE(LOWER(`bussiness`.`nameAr`),'أ','ا'),'أ','ا') ,'ة','ه') LIKE '%test%' )
                  OR( REPLACE( REPLACE(REPLACE(LOWER(`categories2`.`keyWords`),'أ','ا'),'أ','ا') ,'ة','ه') LIKE '%test%' )
                )  
           AND
              (bussiness.bussStatus IN(1,3,5,7)
)
GROUP BY bussiness.bussID  )results
ORDER BY

businessName LIKE '%test%' DESC,
FIELD(bussStatus,'1','5','3'),
FIELD(favor,'1','2','3'),
businessName LIMIT 0,10
我正在使用replace搜索不区分大小写的
أا
㶡ه
字母(在添加测试词之前,我也替换这些字母)

我的问题:

  • 我想知道如何正确地声明索引 我应该声明多列索引:

    ALTER TABLE `bussiness` 
    ADD INDEX `index9` (`nameHe` ASC, `nameEn` ASC, `nameAr` ASC, `favor` ASC, `bussStatus` ASC);
    
    或者每个列有一个列索引

  • 我是否应该创建另一个列
    allNamesLanguages
    ,其中包含
    nameAr、nameEn、nameHe
    ,然后我只搜索这个列

  • 函数基本上使索引无用。因此,在
    WHERE
    子句中使用的列,如
    UPPER(name)
    和else,可以通过所谓的“基于函数的索引”进行索引。它们是Oracle的一个功能,但据我所知,MySQL中没有

    不过,基于函数的索引有其先决条件。所使用的函数必须是确定性的。所以,如果你想索引一个像“年龄”这样的计算,它将不起作用,因为定义为“现在减去然后”的“年龄”基本上在每次选择时都会增长

    我的建议是创建更多的列,并尽可能地存储要挖掘的信息

    如果像“%blabla%”这样使用
    ,由于文本起始长度可变,任何索引都将无效。因此,请尝试组织额外的列,这样您就可以避免像“%…
    这样的
    或根本避免像“
    这样的
    了。根据我的经验,向索引中添加更多的列不会阻碍许多列的性能。因此,只要尝试一下如果为它们添加4列和一个组合索引会发生什么情况

    据我所知,只要你能写下:

    ... WHERE nameEn_idx = 'test' AND/OR nameEr_idx = 'test' ...  
    

    这部分查询存在两个问题,导致标准索引无法使用:

                   ( REPLACE( REPLACE(REPLACE(LOWER(`bussiness`.`nameEn`),'أ','ا'),'أ','ا') ,'ة','ه') LIKE '%test%' )
                  OR( REPLACE( REPLACE(REPLACE(LOWER(`bussiness`.`nameHe`),'أ','ا'),'أ','ا') ,'ة','ه') LIKE '%test%' )
                  OR( REPLACE( REPLACE(REPLACE(LOWER(`bussiness`.`nameAr`),'أ','ا'),'أ','ا') ,'ة','ه') LIKE '%test%' )
                  OR( REPLACE( REPLACE(REPLACE(LOWER(`categories2`.`keyWords`),'أ','ا'),'أ','ا') ,'ة','ه') LIKE '%test%' )
    
    第一个是在列上使用函数。第二个是使用
    like
    和以通配符(
    '%'
    )开头的模式

    对于您似乎想要的功能,您需要使用全文索引、触发器和其他列

    以下是我的建议:

    • 添加(至少)四个用于搜索姓名的附加列。类似于
      business.nameEn\u search
    • 添加
      insert
      ——可能还有
      update
      delete
      触发器,它们将在插入新值时替换特殊字符。也就是说,触发器中包含大量的
      replace(…)
      逻辑
    • 为四列添加全文索引
    • 使用
      match…(匹配)
      进行查询

    有关全文功能的更多信息,请参见。

    并非“业务”的拼写如此。至于索引,为什么不吸一下看看?@草莓我怎么知道我的查询使用了哪些索引!解释会告诉你(我是说“注意”,而不是“不”),这是重复的吗?如果我创建了一个col,谢谢你的回答。”nameEn\u nameAr\u name\u搜索“组合3列,然后只创建一个索引!好吗?2问:我正在使用Innodb引擎,使用全文和匹配是否有问题。。。反对?谢谢,那么创建一个包含四列的列,然后为该列创建一个全文怎么样?哦,根据mysql,需要5.6.4和更高版本,但我使用的是5.6.21b:(感谢您的回复,但这对我没有帮助,因为根据您的查询,名称为testXY的业务将不会返回!还要注意,排序规则utf8\u unicode\u ci和utf8\u persian\u ci会进行大小写折叠。因此,
    UPPER()
    LOWER()
    是不必要的。