AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • Início
  • system&network
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • Início
  • system&network
    • Recentes
    • Highest score
    • tags
  • Ubuntu
    • Recentes
    • Highest score
    • tags
  • Unix
    • Recentes
    • tags
  • DBA
    • Recentes
    • tags
  • Computer
    • Recentes
    • tags
  • Coding
    • Recentes
    • tags
Início / dba / Perguntas / 51947
Accepted
Abdul Manaf
Abdul Manaf
Asked: 2013-10-22 23:05:09 +0800 CST2013-10-22 23:05:09 +0800 CST 2013-10-22 23:05:09 +0800 CST

Converter para Self JOIN

  • 772

Eu tenho uma subconsulta correlacionada, que está levando 16 minutos para ser executada. Como posso convertê-lo para juntar ou otimizá-lo.

SELECT SSF.SM_StockCode, SSF.ST_ItemSize FROM  Stock AS SSF 
    WHERE SSF.SM_StockCode = (
        SELECT SM_StockCode
        FROM  Stock AS SSFAI
        WHERE SSFAI.ST_StockCode = SSF.ST_StockCode
        ORDER BY SSFAI.ST_ItemSize ASC
        LIMIT 1
    ) GROUP BY SSF.SM_StockCode

ATUALIZAÇÃO: Adicionado plano de explicação

+----+--------------------+-------+-------+-------------------+------------------+---------+------+-------+----------------------------------------------+
| id | select_type        | table | type  | possible_keys     | key              | key_len | ref  | rows  | Extra                                        |
+----+--------------------+-------+-------+-------------------+------------------+---------+------+-------+----------------------------------------------+
|  1 | PRIMARY            | SSF   | ALL   | NULL              | NULL             | NULL    | NULL | 45180 | Using where; Using temporary; Using filesort |
|  2 | DEPENDENT SUBQUERY | SSFAI | index | ST_StockCode_Indx | ST_ItemSize_Indx | 9       | NULL |     1 | Using where                                  |
+----+--------------------+-------+-------+-------------------+------------------+---------+------+-------+----------------------------------------------+

ATUALIZAÇÃO: Estrutura da tabela

CREATE TABLE `Stock` (
 `id` int(11) NOT NULL AUTO_INCREMENT,
 `ST_StockCode` varchar(20) NOT NULL,
 `SM_StockCode` varchar(20) NOT NULL,
 `ST_ItemSize` decimal(18,2) NOT NULL,
 PRIMARY KEY (`id`),
 KEY `ST_StockCode_Indx` (`ST_StockCode`),
 KEY `SM_StockCode_Indx` (`SM_StockCode`),
 KEY `ST_ItemSize_Indx` (`ST_ItemSize`)
) ENGINE=MyISAM;
mysql performance
  • 2 2 respostas
  • 161 Views

2 respostas

  • Voted
  1. Best Answer
    ypercubeᵀᴹ
    2013-10-23T06:34:54+08:002013-10-23T06:34:54+08:00

    Você tem SELECT SSF.ST_ItemSizedepois GROUP BY SSF.SM_StockCode, então está usando uma coluna sem agregação na SELECTlista, uma coluna que não está na GROUP BYlista.

    Isso não é um SQL válido pelo padrão de 1992.

    Como ST_ItemSizenão é a chave primária nem tem uma restrição única, o ST_ItemSizenão é funcionalmente dependente dela. Isso torna o código SQL inválido pelos padrões ISO/ANSI mesmo nas versões 2003+ e fornecerá resultados indeterminados (na ST_ItemSizecoluna).

    Infelizmente, o MySQL permite tais consultas (não faz nenhuma verificação de dependência) e é dever do desenvolvedor garantir que uma consulta forneça resultados determinados.

    Portanto, aconselho remover essa consulta do seu código, discutir com os desenvolvedores que a escreveram ou os que a usam e descobrir quais resultados ela deve retornar. Então você pode reescrever.


    Se você ainda quiser executá-lo até fazer isso, o seguinte produzirá resultados semelhantes - e ganhará eficiência por um índice em (ST_StockCode, ST_ItemSize, SM_StockCode):

    SELECT ssf.SM_StockCode, MIN(ssf.ST_ItemSize) AS ST_ItemSize
    FROM  Stock AS ssf 
      JOIN
      ( SELECT ST_StockCode, MIN(ST_ItemSize) AS ST_ItemSize 
        FROM  Stock 
        GROUP BY ST_StockCode 
      ) AS g
      ON  g.ST_StockCode = ssf.ST_StockCode
      AND g.ST_ItemSize = ssf.ST_ItemSize
    GROUP BY ssf.SM_StockCode ;
    
    • 1
  2. Jon of All Trades
    2013-10-23T07:58:12+08:002013-10-23T07:58:12+08:00

    É um pouco difícil dizer o que você está tentando fazer; o que são SM_StockCode e ST_StockCode? Aqui está minha primeira reescrita:

    SELECT
        SM_StockCode, ST_ItemSize
    FROM
        Stock AS S1
    WHERE
        NOT EXISTS (SELECT * FROM Stock AS S2 WHERE S1.SM_StockCode = S2.SM_StockCode AND S1.ST_StockCode = S2.ST_StockCode AND S2.ST_ItemSize > S1.ST_ItemSize)
    GROUP BY
        SM_StockCode, ST_ItemSize
    

    Parece que o que você precisa pode ser tão simples quanto isso:

    SELECT
        SM_StockCode, MIN(ST_ItemSize) AS ST_ItemSize
    FROM
        Stock
    GROUP BY
        SM_StockCode
    

    Se você nos desse alguns dados de amostra, eu poderia estar mais confiante.

    • 1

relate perguntas

  • Onde posso encontrar o log lento do mysql?

  • Como posso otimizar um mysqldump de um banco de dados grande?

  • Quando é o momento certo para usar o MariaDB em vez do MySQL e por quê?

  • Como um grupo pode rastrear alterações no esquema do banco de dados?

Sidebar

Stats

  • Perguntas 205573
  • respostas 270741
  • best respostas 135370
  • utilizador 68524
  • Highest score
  • respostas
  • Marko Smith

    Como fazer a saída do sqlplus aparecer em uma linha?

    • 3 respostas
  • Marko Smith

    Selecione qual tem data máxima ou data mais recente

    • 3 respostas
  • Marko Smith

    Como faço para listar todos os esquemas no PostgreSQL?

    • 4 respostas
  • Marko Smith

    Conceder acesso a todas as tabelas para um usuário

    • 5 respostas
  • Marko Smith

    Listar todas as colunas de uma tabela especificada

    • 5 respostas
  • Marko Smith

    Como usar o sqlplus para se conectar a um banco de dados Oracle localizado em outro host sem modificar meu próprio tnsnames.ora

    • 4 respostas
  • Marko Smith

    Como você mysqldump tabela (s) específica (s)?

    • 4 respostas
  • Marko Smith

    Listar os privilégios do banco de dados usando o psql

    • 10 respostas
  • Marko Smith

    Como inserir valores em uma tabela de uma consulta de seleção no PostgreSQL?

    • 4 respostas
  • Marko Smith

    Como faço para listar todos os bancos de dados e tabelas usando o psql?

    • 7 respostas
  • Martin Hope
    Stéphane Como faço para listar todos os esquemas no PostgreSQL? 2013-04-16 11:19:16 +0800 CST
  • Martin Hope
    Mike Walsh Por que o log de transações continua crescendo ou fica sem espaço? 2012-12-05 18:11:22 +0800 CST
  • Martin Hope
    Stephane Rolland Listar todas as colunas de uma tabela especificada 2012-08-14 04:44:44 +0800 CST
  • Martin Hope
    haxney O MySQL pode realizar consultas razoavelmente em bilhões de linhas? 2012-07-03 11:36:13 +0800 CST
  • Martin Hope
    qazwsx Como posso monitorar o andamento de uma importação de um arquivo .sql grande? 2012-05-03 08:54:41 +0800 CST
  • Martin Hope
    markdorison Como você mysqldump tabela (s) específica (s)? 2011-12-17 12:39:37 +0800 CST
  • Martin Hope
    pedrosanta Listar os privilégios do banco de dados usando o psql 2011-08-04 11:01:21 +0800 CST
  • Martin Hope
    Jonas Como posso cronometrar consultas SQL usando psql? 2011-06-04 02:22:54 +0800 CST
  • Martin Hope
    Jonas Como inserir valores em uma tabela de uma consulta de seleção no PostgreSQL? 2011-05-28 00:33:05 +0800 CST
  • Martin Hope
    Jonas Como faço para listar todos os bancos de dados e tabelas usando o psql? 2011-02-18 00:45:49 +0800 CST

Hot tag

sql-server mysql postgresql sql-server-2014 sql-server-2016 oracle sql-server-2008 database-design query-performance sql-server-2017

Explore

  • Início
  • Perguntas
    • Recentes
    • Highest score
  • tag
  • help

Footer

AskOverflow.Dev

About Us

  • About Us
  • Contact Us

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve