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

Jak pracovat s poddotazy MySQL

Poddotaz je dotaz SQL (Structured Query Language), který je vnořen do jiného dotazu SQL. Příkaz, ve kterém je poddotaz vnořen, se nazývá nadřazený dotaz. Poddotazy se používají k předběžnému zpracování dat, která se používají v nadřazeném dotazu. Poddotazy lze použít v SELECT , INSERT , UPDATE a DELETE operace.

Při provádění poddotazů je poddotaz zpracován jako první před nadřazeným dotazem. Při vytváření aplikací MySQL nabízí použití poddotazů několik výhod:

  • Rozdělují příkazy SQL do jednoduchých logických celků, což usnadňuje jejich pochopení a údržbu. Jinými slovy, dílčí dotazy pomáhají izolovat složité části dotazů.
  • Odstraňují potřebu používat složitýUNION prohlášení a JOIN prohlášení.
  • Používají se k vynucení referenční integrity ve scénáři, kde nejsou implementovány cizí klíče.
  • Pomáhají vývojářům kódovat obchodní logiku do dotazů MySQL.

V této příručce se dozvíte:

  • Jak používat korelovaný poddotaz
  • Jak používat korelovaný poddotaz v operátoru porovnání
  • Jak používat poddotaz jako odvozenou tabulku

Než začnete

Chcete-li pokračovat v této příručce, ujistěte se, že máte následující:

  1. Pokud jste tak ještě neučinili, vytvořte si účet Linode a Compute Instance. Podívejte se na naše příručky Začínáme s Linode a Vytvoření výpočetní instance.

  2. Při aktualizaci systému postupujte podle našeho průvodce nastavením a zabezpečením výpočetní instance. Můžete také chtít nastavit časové pásmo, nakonfigurovat název hostitele, vytvořit omezený uživatelský účet a posílit přístup SSH.

  3. Serverový software MySQL (nebo MariaDB) nainstalovaný na vašem Linode. Podívejte se prosím do sekce MySQL, která obsahuje průvodce popisující, jak nainstalovat MySQL na několik distribucí Linuxu.

Nastavení databáze

Chcete-li pochopit, jak fungují poddotazy, vytvořte nejprve ukázkovou databázi. Tato ukázková databáze se používá ke spouštění různých příkladů dotazů v této příručce:

  1. SSH na váš server a přihlaste se k MySQL jako root:

     mysql -u root -p
    

    Po zobrazení výzvy zadejte heslo uživatele root vašeho serveru MySQL a stiskněte Enter pokračovat. Všimněte si, že root heslo vašeho MySQL serveru není stejné jako root heslo vašeho Linode.

    Poznámka

    Pokud vaše heslo nebude přijato, možná budete muset spustit předchozí příkaz pomocí sudo :

    sudo mysql -u root -p
    
  2. Pokud je vaše heslo přijato, měli byste vidět výzvu MySQL:

    
    mysql >
    
    Poznámka

    Pokud používáte MariaDB, může se vám místo toho zobrazit výzva podobná následující:

    
    MariaDB [(none)]>
    
  3. Chcete-li vytvořit ukázkovou databázi s názvem test_db , spustit:

    CREATE DATABASE test_db;
    

    Měli byste vidět tento výstup, který potvrzuje, že databáze byla úspěšně vytvořena:

    
    Query OK, 1 row affected (0.01 sec)
    
  4. Přepněte na test_db databáze:

    USE test_db;
    

    Měli byste vidět tento výstup:

    
    Database changed
    
  5. Vytvořili jste test_db a vybral to. Dále vytvořte tabulku s názvem customers :

     CREATE TABLE customers
     (
     customer_id BIGINT PRIMARY KEY AUTO_INCREMENT,
     customer_name VARCHAR(50)
     ) ENGINE = InnoDB;
    

    Měli byste vidět tento výstup:

    
    Query OK, 0 rows affected (0.03 sec)
    
  6. Přidejte nějaké záznamy do customers stůl. Spusťte níže uvedený příkaz INSERT příkazy jeden po druhém:

    INSERT INTO customers(customer_name) VALUES ('JOHN PAUL');
    INSERT INTO customers(customer_name) VALUES ('PETER DOE');
    INSERT INTO customers(customer_name) VALUES ('MARY DOE');
    INSERT INTO customers(customer_name) VALUES ('CHRISTINE JAMES');
    INSERT INTO customers(customer_name) VALUES ('MARK WELL');
    INSERT INTO customers(customer_name) VALUES ('FRANK BRIAN');
    

    Tento výstup se zobrazí po vložení každého záznamu:

    
    Query OK, 1 row affected (0.00 sec)
    ...
    
  7. Ověřte, že informace o zákaznících byly vloženy do databáze. Spusťte tento SELECT příkaz:

    SELECT * FROM customers;
    

    Měli byste vidět tento seznam zákazníků:

    
    +-------------+-----------------+
    | customer_id | customer_name   |
    +-------------+-----------------+
    |           1 | JOHN PAUL       |
    |           2 | PETER DOE       |
    |           3 | MARY DOE        |
    |           4 | CHRISTINE JAMES |
    |           5 | MARK WELL       |
    |           6 | FRANK BRIAN     |
    +-------------+-----------------+
    6 rows in set (0.00 sec)
    
  8. Vytvořte sales stůl. Tato tabulka používá sloupec customer_id odkazovat na customers tabulka:

    CREATE TABLE sales
    (
    order_id BIGINT PRIMARY KEY AUTO_INCREMENT,
    customer_id BIGINT,
    sales_amount DECIMAL(17,2)
    ) ENGINE = InnoDB;
    

    Zobrazí se tento výstup:

    
    Query OK, 0 rows affected (0.03 sec)
    
  9. Dále vyplňte sales tabulka s některými záznamy. Spusťte níže uvedený příkaz INSERT příkazy jeden po druhém:

    INSERT INTO sales (customer_id, sales_amount) VALUES ('1','25.75');
    INSERT INTO sales (customer_id, sales_amount) VALUES ('2','85.25');
    INSERT INTO sales (customer_id, sales_amount) VALUES ('5','3.25');
    INSERT INTO sales (customer_id, sales_amount) VALUES ('4','200.75');
    INSERT INTO sales (customer_id, sales_amount) VALUES ('5','88.10');
    INSERT INTO sales (customer_id, sales_amount) VALUES ('1','100.00');
    INSERT INTO sales (customer_id, sales_amount) VALUES ('2','45.00');
    INSERT INTO sales (customer_id, sales_amount) VALUES ('4','15.80');
    

    Tento výstup se zobrazí po vložení každého záznamu:

    
    Query OK, 1 row affected (0.01 sec)
    ...
    
  10. Ověřte údaje v sales stůl. Spusťte tento SELECT příkaz:

    SELECT * FROM sales;
    

    Nyní by se měl zobrazit tento seznam údajů o prodeji:

    
    +----------+-------------+--------------+
    | order_id | customer_id | sales_amount |
    +----------+-------------+--------------+
    |        1 |           1 |        25.75 |
    |        2 |           2 |        85.25 |
    |        3 |           5 |         3.25 |
    |        4 |           4 |       200.75 |
    |        5 |           5 |        88.10 |
    |        6 |           1 |       100.00 |
    |        7 |           2 |        45.00 |
    |        8 |           4 |        15.80 |
    +----------+-------------+--------------+
    8 rows in set (0.00 sec)
    

Po nastavení databáze a souvisejících tabulek nyní můžete implementovat různé poddotazy v MySQL.

Jak používat korelovaný poddotaz

Korelovaný poddotaz je typ vnořeného dotazu, který používá hodnoty z nadřazeného dotazu. Tyto druhy dotazů odkazují na nadřazený dotaz se sloupcem. Vnořený dotaz se provede jednou pro každý řádek v nadřazeném dotazu.

Níže uvedený příklad představuje dotaz, který vybere všechny zákazníky. Uvnitř dotazu je korelovaný dílčí dotaz, který načte celkovou částku prodeje pro každého zákazníka z sales tabulka.

  1. Spusťte příklad dotazu:

    SELECT
    customer_id,
    customer_name,
    (SELECT SUM(sales_amount)
    FROM sales WHERE customer_id = customers.customer_id) as total_sales_amount
    FROM
    customers;
    

    V tomto příkladu je poddotaz SELECT SUM(sales_amount) FROM sales WHERE customer_id = customers.customer_id , který je uveden v závorkách.

    Zobrazí se seznam celkových prodejů uskutečněných zákazníky:

    
    +-------------+-----------------+--------------------+
    | customer_id | customer_name   | total_sales_amount |
    +-------------+-----------------+--------------------+
    |           1 | JOHN PAUL       |             125.75 |
    |           2 | PETER DOE       |             130.25 |
    |           3 | MARY DOE        |               NULL |
    |           4 | CHRISTINE JAMES |             216.55 |
    |           5 | MARK WELL       |              91.35 |
    |           6 | FRANK BRIAN     |               NULL |
    +-------------+-----------------+--------------------+
    6 rows in set (0.00 sec)
    

    Výše uvedený výstup z korelovaného dílčího dotazu vám může poskytnout souhrnný seznam objednávek zákazníků. Vezměte prosím na vědomí, protože customer_id s 3 a 6 nemají žádné přidružené záznamy v tabulce prodejů, jejich total_sales_amount je NULL .

  2. Elegantnějším způsobem prezentace tohoto seznamu je vrátit 0 místo NULL pro zákazníky s nulovým prodejem. Chcete-li to provést, uzavřete výstup generovaný poddotazem pomocí IFNULL(expression, 0) prohlášení. Spusťte tento aktualizovaný příkaz:

     SELECT
     customer_id,
     customer_name,
     IFNULL((SELECT SUM(sales_amount)
     FROM sales WHERE customer_id = customers.customer_id), 0) as total_sales_amount
     FROM
     customers;
    

    Zobrazí se následující výstup. MySQL vrací 0,00 pro všechny řádky, které by jinak vrátily NULL hodnoty.

    
    +-------------+-----------------+--------------------+
    | customer_id | customer_name   | total_sales_amount |
    +-------------+-----------------+--------------------+
    |           1 | JOHN PAUL       |             125.75 |
    |           2 | PETER DOE       |             130.25 |
    |           3 | MARY DOE        |               0.00 |
    |           4 | CHRISTINE JAMES |             216.55 |
    |           5 | MARK WELL       |              91.35 |
    |           6 | FRANK BRIAN     |               0.00 |
    +-------------+-----------------+--------------------+
    6 rows in set (0.00 sec)
    

    Tento přístup pomáhá zajistit, že výstup nepoškodí žádné další výpočty v záznamech.

Jak používat korelovaný poddotaz v porovnávacím operátoru

Poddotazy jsou užitečné pro přesun obchodní logiky na úroveň databázového dotazu. Následující obchodní případy použití obsahují korelované poddotazy umístěné v klauzuli WHERE nadřazeného dotazu:

  • Zvažte scénář, kdy byste chtěli získat seznam všech zákazníků registrovaných v databázi, kteří nemají přidružené prodeje. Poddotaz můžete použít společně s operátorem porovnání MySQL NOT IN a získat tyto zákazníky:

      SELECT
      customer_id,
      customer_name
      FROM
      customers
      WHERE customer_id NOT IN (SELECT customer_id FROM sales);
    

    V tomto příkladu je poddotaz SELECT customer_id FROM sales , který je uveden v závorkách. Příkaz SQL uvedený výše zobrazí seznam dvou zákazníků, kteří nejsou nalezeni v tabulce prodejů:

    
    +-------------+---------------+
    | customer_id | customer_name |
    +-------------+---------------+
    |           3 | MARY DOE      |
    |           6 | FRANK BRIAN   |
    +-------------+---------------+
    2 rows in set (0.00 sec)
    

    V produkčním prostředí můžete tento druh sady záznamů použít k lepším obchodním rozhodnutím. Můžete například vytvořit skript pomocí jiného jazyka, jako je PHP nebo Python, k odeslání e-mailu těmto zákazníkům a dotazu, zda nemají problém s objednávkou.

  • Dalším případem použití je čištění dat. Můžete například použít dílčí dotaz k odstranění zákazníků, kteří nikdy nezadali objednávku:

      DELETE
      FROM
      customers
      WHERE customer_id NOT IN (SELECT customer_id FROM sales);
    

    Příkaz SQL výše odstraní dva zákazníky a zobrazí následující:

    
    Query OK, 2 rows affected (0.01 sec)
    

    Pokud znovu spustíte příkaz pro seznam všech zákazníků, tito zákazníci by se již neměli v tabulce objevovat:

      SELECT *
      FROM
      customers;
    

    Níže uvedený výstup potvrzuje, že zákazníci bez přidružených objednávek byli smazáni:

    
    +-------------+-----------------+
    | customer_id | customer_name   |
    +-------------+-----------------+
    |           1 | JOHN PAUL       |
    |           2 | PETER DOE       |
    |           4 | CHRISTINE JAMES |
    |           5 | MARK WELL       |
    +-------------+-----------------+
    4 rows in set (0.00 sec)
    

Jak používat poddotaz jako odvozenou tabulku

Když jsou poddotazy použity v FROM klauzule nadřazeného dotazu, jsou označovány jako odvozené tabulky . Jsou velmi důležité při implementaci složitých dotazů, které by jinak vyžadovaly VIEW MySQL , JOIN nebo UNION doložka. Odvozená tabulka existuje v dotazu, který ji vytvořil, a není trvale uložena do databáze.

Když jsou poddotazy použity jako odvozené tabulky, izolují různé části příkazu SQL. Jinými slovy, poddotaz poskytuje zjednodušený výraz tabulky, který lze použít v rámci nadřazeného dotazu.

Poznámka Pamatujte, že každá odvozená tabulka musí mít alias.

Spuštěním příkazu níže vytvořte odvozený poddotaz tabulky s aliasem order_summary :

SELECT customer_id
FROM
    (
    SELECT
    customer_id,
    count(order_id) as total_orders
    FROM sales
    group by customer_id
    ) as order_summary
WHERE order_summary.total_orders > 1;
Poznámka

V tomto příkazu se poddotaz zobrazí v závorkách jako:

SELECT
customer_id,
count(order_id) as total_orders
FROM sales
group by customer_id

Výše uvedený příkaz se dotazuje na prodejní tabulku, aby určil zákazníky s více než 1 objednávkou. Po spuštění dotazu se zobrazí tento výstup:


+-------------+
| customer_id |
+-------------+
|           1 |
|           2 |
|           5 |
|           4 |
+-------------+
4 rows in set (0.00 sec)

Výše uvedený seznam obsahuje čtyři customer_id s, které mají více než jednu objednávku. Jako příklad obchodního použití můžete takový dotaz použít ve skriptu, který odmění zákazníky bonusem při jejich příštím nákupu.

Další informace

Další informace o tomto tématu můžete získat v následujících zdrojích. Přestože jsou poskytovány v naději, že budou užitečné, vezměte prosím na vědomí, že nemůžeme ručit za přesnost nebo aktuálnost externě hostovaných materiálů.

  • Poddotazy MySQL

  1. jak nahradit písmeno s diakritikou ve sloupci varchar2 v oracle

  2. Jak odstranit úvodní a/nebo koncové mezery řetězce v T-SQL

  3. Jaký je nejrychlejší způsob hromadného vkládání velkého množství dat na SQL Server (klient C#)

  4. Kontrola konce hodnoty dlouhé proměnné ve VBA