Eu tenho uma tabela mysql simples:
CREATE TABLE IF NOT EXISTS `pers` (
`persID` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(35) NOT NULL,
`gehalt` int(11) NOT NULL,
`chefID` int(11) DEFAULT NULL,
PRIMARY KEY (`persID`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 AUTO_INCREMENT=4 ;
INSERT INTO `pers` (`persID`, `name`, `gehalt`, `chefID`) VALUES
(1, 'blb', 1000, 3),
(2, 'as', 1000, 3),
(3, 'chef', 1040, NULL);
Tentei executar a atualização seguinte, mas recebo apenas o erro 1093:
UPDATE pers P
SET P.gehalt = P.gehalt * 1.05
WHERE (P.chefID IS NOT NULL
OR gehalt <
(SELECT (
SELECT MAX(gehalt * 1.05)
FROM pers MA
WHERE MA.chefID = MA.chefID)
AS _pers
))
Procurei o erro e encontrei no mysql a seguinte página http://dev.mysql.com/doc/refman/5.1/en/subquery-restrictions.html , mas isso não me ajuda.
O que devo fazer para corrigir a consulta sql?
sql
mysql
mysql-error-1093
CSchulz
fonte
fonte
Respostas:
O problema é que o MySQL, por qualquer motivo insano, não permite que você escreva consultas como esta:
Ou seja, se você estiver fazendo um
UPDATE
/INSERT
/DELETE
em uma tabela, não poderá fazer referência a essa tabela em uma consulta interna ( no entanto, você pode fazer referência a um campo dessa tabela externa ...)A solução é substituir a instância da
myTable
subconsulta por(SELECT * FROM myTable)
, assim:Aparentemente, isso faz com que os campos necessários sejam copiados implicitamente em uma tabela temporária, portanto é permitido.
Encontrei esta solução aqui . Uma observação desse artigo:
fonte
T
e(SELECT * FROM T)
são completamente equivalentes. Eles são a mesma relação. Portanto, essa é uma restrição arbitrária e sem sentido. Mais especificamente, é uma solução alternativa para coagir o MySQL a fazer algo que claramente pode fazer, mas, por algum motivo, não pode analisar em sua forma mais simples.DELETE FROM t WHERE tableID NOT IN (SELECT viewID FROM t_view);
Também recomendo correrOPTIMIZE TABLE t;
depois para reduzir o tamanho da tabela.Você pode fazer isso em três etapas:
...
ou
fonte
CREATE TABLE
instruções - espero que o autor esteja ciente disso. No entanto, esta é a única solução? Ou a consulta pode ser reescrita com subconsultas ou junções? E por que (não) faz isso?UPDATE Pers P
lerUPDATE pers P
?CREATE TABLE AS SELECT
dá um desempenho horrível?No Mysql, você não pode atualizar uma tabela subconsultando a mesma tabela.
Você pode separar a consulta em duas partes ou fazer
fonte
SELECT ... SET
? Eu nunca ouvi falar disso.AS B
na segunda referência aTABLE_A
. a resposta no exemplo mais votado pode ser simplificada usando emAS T
vez do potencialmente ineficienteFROM (SELECT * FROM myTable) AS something
, que felizmente o otimizador de consultas normalmente elimina, mas nem sempre o faz.Criar uma tabela temporária (tempP) a partir de uma subconsulta
Introduzi um nome separado (alias) e atribui um novo nome à coluna 'persID' da tabela temporária
fonte
SELECT ( SELECT MAX(gehalt * 1.05)..
- o primeiroSELECT
não seleciona nenhuma coluna.É bem simples Por exemplo, em vez de escrever:
você deveria escrever
ou similar.
fonte
A Abordagem publicada por BlueRaja é lenta. Modifiquei-a como estava usando para excluir duplicatas da tabela. Caso ajude qualquer pessoa com tabelas grandes Consulta Original
Isso está levando mais tempo:
Solução mais rápida
fonte
Apenas como referência, você também pode usar variáveis Mysql para salvar resultados temporários, por exemplo:
https://dev.mysql.com/doc/refman/5.7/en/user-variables.html
fonte
Se você estiver tentando ler o campoA da tabelaA e salvá-lo no campoB na mesma tabela, quando o campoc = campod, convém considerar isso.
O código acima copia o valor do campo A para o campo B quando o campo de condição atendeu à sua condição. isso também funciona no ADO (por exemplo, acesso)
fonte: tentei-me
fonte
O MariaDB levantou isso a partir do 10.3.x (para
DELETE
eUPDATE
):DBFiddle MariaDB 10.2 - Erro
DBFiddle MariaDB 10.3 - Sucesso
fonte
Outras soluções alternativas incluem o uso de SELECT DISTINCT ou LIMIT na subconsulta, embora não sejam tão explícitos em seus efeitos na materialização. isso funcionou para mim
como mencionado no MySql Doc
fonte
O MySQL não permite selecionar de uma tabela e atualizar na mesma tabela ao mesmo tempo. Mas sempre há uma solução alternativa :)
Isso não funciona >>>>
Mas isso funciona >>>>
fonte