sql >> Databáze >  >> RDS >> Mysql

Jak spustit stejný dotaz proti více tabulkám v databázi

FROM část SELECT příkaz musí mít skutečné názvy tabulek, nikoli CHAR(100) proměnná, která obsahuje název tabulky. Takto to prostě nefunguje.

Vypadá to, že chcete spustit konkrétní dotaz proti mnoha tabulkám s podobnou strukturou ve vaší databázi. Docela často to znamená, že schéma databáze by mohlo být vylepšeno. Ale pokud se musíte vypořádat s tím, co máte, budete muset použít dynamické SQL . Tento odkaz na dokumentaci MySQL obsahuje příklad „který ukazuje, jak vybrat tabulku, na kterou se má provést dotaz za běhu, uložením názvu tabulky jako uživatelské proměnné“, což je přesně to, co potřebujete.

Uvnitř vaší smyčky musíte vytvořit řetězec s SQL dotazem a použít EXECUTE .

SET @s = CONCAT('select count(distinct signature) from ', tableName);

PREPARE stmt FROM @s;
EXECUTE stmt;
DEALLOCATE PREPARE stmt;

Pokud jsem pochopil, výsledek příkazu EXECUTE je odeslána volajícímu uložené procedury, jako by to byl normální SELECT , takže v tomto příkladu volající obdrží více sad výsledků, pokud má vaše databáze více než jednu tabulku where table_name like "%FAULT_20150320%" .

Zde je odkaz na další otázku SO ohledně dynamického SQL MySQL Jak mít dynamické SQL v MySQL uložené procedury s několika příklady.

Vypadá to, že něco takového chceš. Měl by sčítat počty z několika tabulek v signatureCount proměnná.

CREATE PROCEDURE CountSignatures()
BEGIN
    DECLARE done INT DEFAULT FALSE;
    DECLARE signatureCount INT;
    DECLARE tableName CHAR(100);
    DECLARE tableList CURSOR FOR SELECT table_name FROM information_schema.tables WHERE table_name LIKE "%FAULT_20150320%";
    DECLARE CONTINUE HANDLER FOR NOT FOUND SET done = TRUE;
    SET signatureCount = 0;
    OPEN tableList;
    tableListLoop: LOOP
        SET done = FALSE;
        FETCH tableList INTO tableName;
        IF done THEN
            LEAVE tableListLoop;
        END IF;

        SET @VarCount = 0;
        SET @VarSQL = CONCAT('SET @VarCount = (SELECT COUNT(DISTINCT signature) FROM ', tableName, ')');

        PREPARE stmt FROM @VarSQL;
        EXECUTE stmt;
        DEALLOCATE PREPARE stmt;

        SET signatureCount = signatureCount + @VarCount;
    END LOOP;
    CLOSE tableList;

    SELECT signatureCount;
END$$

Další variantou, pokud počet tabulek, které potřebujete zpracovat, není mnoho, je vytvořit dynamicky jeden velký SQL příkaz, který zahrnuje všechny tabulky uvnitř vaší smyčky a poté EXECUTE na jeden zátah:

SELECT 
(COUNT(DISTINCT signature) FROM Table1) +
(COUNT(DISTINCT signature) FROM Table2) +
...
(COUNT(DISTINCT signature) FROM TableN) AS TotalCount


  1. Jak načíst číslo uzlu založené na nadřazeném uzlu dynamicky ze souboru xsd pomocí PHP

  2. Jak nasadit Teamcity s PostgreSQL pro vysokou dostupnost

  3. Express.js a MySQL model + validace

  4. přesunout tabulku z jednoho schématu do jiného schématu?