【问题标题】:PHP MySQL performance advicePHP MySQL 性能建议
【发布时间】:2018-01-31 21:43:52
【问题描述】:

我有一张名为house 的表。

house 表有 32 列(id、name、floors、doors、color、windows 等)。所以基本上是一个包含不同数据类型(varchar、int、decimal、enum 等)的不同列的表。

现在假设表有 500,000 行。

现在我有了我的用户。他们可以创建一个“房屋搜索”,在其中选择所有 32 列搜索什么。

“房屋搜索”也存储在另一个表 house_search 中。我基本上用所有选定的值做一个简单的INESRT INTO

在执行此操作时,我想检查表 house 是否有任何“匹配”。

如果我有匹配项,我想将此匹配项插入另一个表 house_match

问题是我想为搜索打分,所以我不能简单地创建我的 SELECT 来查找正确的行。

长话短说:将给定的“房屋搜索”与所有 500,000 行进行比较的最佳方法是什么?

现在我将“搜索”详细信息存储在 MYSQLI_ASSOC 数组中,然后选择所有房屋并遍历每一行并调用一个进行比较的函数。

问题:非常慢!

// Get the house search data
$sql = "SELECT columnsWeNeedForTheComparison
          FROM house_search
         WHERE id = ". $_POST['housesearchid'] .";";
$result = $mySQLi->query($sql); 
$searchHouse = $result->fetch_assoc();

$sql = "SELECT everyThingFromHouseTableWeNeed
          FROM house INNER JOIN ...
                     INNER JOIN ...;";
$result = $mySQLi->query($sql);
while($checkHouse = $result->fetch_assoc())
{
     // call comparison function
     $matchPoints = __checkHouseMatch($searchHouse, $checkHouse);

     if($matchPoints > 100)
     {
          $sql = "INSERT INTO house_match
                      ( ..... );";
          $insert = $mySQLi->query($sql);
     }
}

__checkHouseMatch()函数中我做了这样的事情

if($searchHouse['buildyear'] == $checkHouse['buildyear'])
{
    $matchPoints += 10;
}
else if($searchHouse['buildyear'] == $checkHouse['buildyear'])
{
    $matchPoints += 5;
}

如果匹配点是例如> 100 我将INSERT INTO 转换为house_match

 INSERT INTO house_match
     ( housesearchid, houseid )
 VALUES
     ( ". $houseSearchID .", ". $houseID ." );

最好的方法是什么?

我可以考虑

  • 将所有房屋存储在一个数组中?
  • Cronjob 在晚上不管花多长时间?

非常感谢任何建议!干杯:-)

【问题讨论】:

  • 32 列??我会先改变它的结构..添加 i.E. fk 并创建其他表“房屋详细信息”
  • 干杯塔德曼!我也使用准备好的语句。所以上面所有的陈述都准备好了。为了更好地理解,我选择给出正常的陈述!
  • 感谢 pbalazek!不明白有什么好处?我只在列中存储简单的值(门=2,颜色=1(这是表颜色的 FK),使用房屋=y 等等
  • 不要通过内联代码和添加明显的 SQL 注入错误来“简化”您的代码。它不仅会助长坏习惯,还会让你看起来邋遢,并立即对代码的其余部分产生怀疑。像这样的内联内容对理解的唯一作用就是传达一种理解,即你在玩火。
  • 这也促使人们练习他们的评论宏。

标签: php mysql database loops


【解决方案1】:

我认为对于您正在尝试做的事情,您的表格格式是错误的。

像 house_data: (id, house_id(FK), field, data) 这样的表会更好。您还有另一个名为 house: (id, ...) 的表,但没有 windows 等属性。

所以在 house_data 上你会拥有,例如:

id: 12
house_id: 30 (foreign key to house table)
field: windows
data: double-paned

我不推荐任何特定的索引,因为我不确定您的搜索焦点是否与房屋的属性或属性中的数据更相关;这会有所作为。

【讨论】:

  • 干杯Difster!听起来不错。也许我尝试这种方法。从来没想过。桌子最后会不会很大?我有 500,000 个房屋 x 32 个“字段行”= 16.000.000 行。真的会更快吗?
  • 我认为搜索可能会更快,是的。例如,如果您只想查询窗口,则不必搜索所有记录,只需搜索 field = "windows" 的记录,然后搜索相关数据。在数据方面,由于用例不同,从来没有一种正确的方法。但是,我发现与其存储许多不同的列名,我更喜欢这种方法,因为如果我需要添加它,那么我不必更改我的表,只需插入更多数据。
  • 听起来合法!我一定会试试这个。谢谢!
  • 确实,对于这种数据集,您可能想尝试使用 Elastic Search 以及我建议的表格格式。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-12-28
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多