Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/247.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
Php Mysql查询执行起来需要很多时间_Php_Mysql - Fatal编程技术网

Php Mysql查询执行起来需要很多时间

Php Mysql查询执行起来需要很多时间,php,mysql,Php,Mysql,我正在开发一个时间表应用程序,并编写一个PHP代码来获取截止日期的所有时间表。这是我为获取时间表而编写的查询- 选择a.accnt\u名称、u.username、DATE\u格式(t.in\u time、%H:%i')inTime、DATE\u格式(t.out\u time、%H:%i')outTime、DATE\u格式(t.work\u time、%H:%i')workTime、w.wrktyp\u name、t.备注、DATE\u格式(t.tmsht\u DATE、%d-%b-%Y')tms

我正在开发一个时间表应用程序,并编写一个PHP代码来获取截止日期的所有时间表。这是我为获取时间表而编写的查询-

选择a.accnt\u名称、u.username、DATE\u格式(t.in\u time、%H:%i')inTime、DATE\u格式(t.out\u time、%H:%i')outTime、DATE\u格式(t.work\u time、%H:%i')workTime、w.wrktyp\u name、t.备注、DATE\u格式(t.tmsht\u DATE、%d-%b-%Y')tmshtDate、wl.loctn\u名称、s.serv\u名称、t.status\u代码、t.convkms convkms convkms convkms、convamount FROM,账户a、服务s、工作类型w、工作地点wl、其中a.accnt_代码=t.accnt_代码和w.wrktyp_代码=t.wrktyp_代码和wl.loctn_代码=t.loctn_代码和s.serv_代码=t.serv_代码和t.usr_代码=u的用户。按tmsht_日期说明订购

where子句包含从各个表中获取各个代码的实际值的子句

问题是执行此查询需要花费大量时间,并且应用程序在几分钟后崩溃

我在phpmyadmin中运行了这个查询,在那里它可以正常工作


需要帮助了解执行缓慢背后的原因。

phpadmin会自动为查询添加限制,这就是为什么您可以快速获得结果

  • 检查表中有多少行
  • 使用limit运行您的查询

  • 使用EXPLAIN查看查询的执行计划。确保MySQL有合适的可用索引,并且正在使用这些索引

    查询文本似乎缺少此处列的名称

      t.usr_code = u.    ORDER
                     ^^^
    
    我们可以“猜测”那应该是
    u.usr\u code
    ,但那只是猜测

    应该返回多少行?结果集有多大

    您的客户端是否试图“存储”内存中的所有行,并因为内存不足而崩溃

    如果是这样,我建议您避免这样做,并根据需要获取行

    或者,考虑在WHERE子句中添加一些额外的谓词来返回您需要的行,而不是返回表中的所有行。

    现在是2015年。是时候抛弃join操作的老式逗号语法了,改用
    join
    关键字,并将join谓词从
    WHERE
    子句移动到
    ON
    子句。并格式化它。数据库并不在意,但它会让需要破译SQL语句的可怜人更容易理解

      SELECT a.accnt_name
           , u.username
           , DATE_FORMAT(t.in_time  ,'%H:%i') AS inTime
           , DATE_FORMAT(t.out_time ,'%H:%i') AS outTime
           , DATE_FORMAT(t.work_time,'%H:%i') AS workTime
           , w.wrktyp_name
           , t.remarks
           , DATE_FORMAT(t.tmsht_date, '%d-%b-%Y') AS tmshtDate
           , wl.loctn_name
           , s.serv_name
           , t.status_code
           , t.conv_kms      AS convkms
           , t.conv_amount   AS convamount 
        FROM timesheets t
        JOIN accounts a
          ON a.accnt_code = t.accnt_code
        JOIN services s
          ON s.serv_code = t.serv_code 
        JOIN worktypes w
          ON w.wrktyp_code = t.wrktyp_code
        JOIN work_location wl
          ON wl.loctn_code = t.loctn_code 
        JOIN users
          ON u.usr_code = t.usr_code
       ORDER BY t.tmsht_date DESC
    
    格式化日期列上的排序非常奇怪。更可能的情况是,您希望结果以“日期”顺序返回,而不是以字符串顺序返回,以月份和日期为前一年。(您真的想先按日期值排序,在年份之前吗?)

    跟进

    如果使用来自不同客户机(同一数据库、同一用户)的整个结果集(约720行)快速完成相同的精确查询,那么问题可能不是此SQL语句

      SELECT a.accnt_name
           , u.username
           , DATE_FORMAT(t.in_time  ,'%H:%i') AS inTime
           , DATE_FORMAT(t.out_time ,'%H:%i') AS outTime
           , DATE_FORMAT(t.work_time,'%H:%i') AS workTime
           , w.wrktyp_name
           , t.remarks
           , DATE_FORMAT(t.tmsht_date, '%d-%b-%Y') AS tmshtDate
           , wl.loctn_name
           , s.serv_name
           , t.status_code
           , t.conv_kms      AS convkms
           , t.conv_amount   AS convamount 
        FROM timesheets t
        JOIN accounts a
          ON a.accnt_code = t.accnt_code
        JOIN services s
          ON s.serv_code = t.serv_code 
        JOIN worktypes w
          ON w.wrktyp_code = t.wrktyp_code
        JOIN work_location wl
          ON wl.loctn_code = t.loctn_code 
        JOIN users
          ON u.usr_code = t.usr_code
       ORDER BY t.tmsht_date DESC
    
    我们不希望SQL语句的执行导致PHP“崩溃”

    如果要存储整个结果集(例如,使用mysqli store_result),则需要有足够的内存。但是select列表中的13个表达式看起来都相对较短(格式化日期、名称和代码),我们不希望“备注”超过几KB

    如其他人所建议的那样,为了调试此操作,请尝试在查询中添加一个LIMIT子句,例如
    LIMIT 1
    ,并观察其行为

    或者,使用虚拟查询进行测试;使用保证返回特定值和特定行数的查询

      SELECT 'morpheus'             AS accnt_name
           , 'trinity'              AS username
           , '01:23'                AS inTime
           , '04:56'                AS outTime
           , '00:45'                AS workTime
           , 'neo'                  AS wrktyp_name
           , 'yada yada yada'       AS remarks
           , '27-May-2015'          AS tmshtDate
           , 'zion'                 AS loctn_name
           , 'nebuchadnezzar'       AS serv_name
           , ''                     AS status_code
           , '123'                  AS convkms
           , '5678'                 AS convamount 
    
    我怀疑该查询不是您正在观察的行为的根本原因。我怀疑问题出在代码的其他地方


    首先:修改您的查询,使其看起来像斯宾塞给出的查询

    当你的应用程序“崩溃”时,你会收到错误消息吗?还是只是停止了

    你可以试试:

    ini_set('max_execution_time', 0);
    
    在php代码中。这将最大执行时间设置为无限。因此,如果没有错误,脚本应该执行到最后。因此,您可以查看查询是否得到所需的结果

    同样,作为一个测试,使用

     LIMIT 10
    
    这将大大加快您的查询速度,因为它只需要前十个结果。
    您可以稍后将此值更改为更适合您需要的值。除非您绝对需要完整的结果集,否则我建议您在查询中始终使用LIMIT。

    可以对选择的字段使用索引以加快执行速度感谢您的详细回答。我完全同意应该使用JOIN而不是传统的where子句。你关于根据格式化日期排序的观点也是很好的。我没有注意到这一点。然而,即使我将代码更改为您给出的代码,问题仍然存在。这是我第一次面对这样的问题。而且关于结果中记录的数量不是很高。大约有720条记录。我也相信这个查询不是你问题的原因。您是运行本地sql server还是在共享主机上运行sql server?几年前,我是一家sharede托管服务公司,由于产能过剩,它的sql server速度非常慢。一个简单的sql语句花费的时间太长。也许你也是这样。我正在运行一个本地mysql实例。我在一个共享主机上也有它,但是我的本地实例本身有问题。
    max\u execution\u time
    设置有点有用。页面运行了很长时间,没有出现错误,但它打印了我给出的几个回音。