zoukankan      html  css  js  c++  java
  • Sql:基础

    本文根据书籍《sql必知必会》,整理而成。

    基本概念

    数据库 database:保存有组织的数据的容器,通常是一个文件或一组文件。

    数据库管理系统 DBMS:又称数据库软件,数据库是通过 DBMS 创建和操纵的容器。

    表 table:某种特定类型数据的结构化清单。

    模式 schema:关于数据库和表的布局及特性的信息。

    列 column:表中的一个字段。所有的表都是由一个或多个列组成的。

    行 row:表中的一个记录,有时又称为数据库记录 record。

    主键 primary key:一列(或一组列),其值能够唯一标识表中每一行。

    关键字 keyword:作为 SQL 组成部分的保留字。

    子句 clause:SQL 语句由子句构成,有些子句是必需的,有些则是可选的。一个子句通常由一个关键字加上所提供的数据组成。例如 SELECT 语句中的 FROM 子句。 

    SQL 是结构化查询语言(structured query language)的缩写。SQL 是一种专门用来与数据库沟通的语言。

    检索数据

    基本查询用 SELECT 语句

    SELECT DISTINCT prod_id, prod_name FROM Products LIMIT 5 OFFSET 5;

    注意:DISTINCT 关键字作用于所有的列。LIMIT 5 OFFSET 5 指示 MySQL 等 DBMS 返回从第 5 行起的 5 行数据。第一个数字是指从哪儿开始,第二个数字是检索的行数。

    排序数据

    SELECT prod_id, prod_price, prod_name FROM Products ORDER BY prod_price DESC, prod_name;

    注意:ORDER BY 子句必须是 SELECT 语句中的最后一条子句。同时使用 ORDER BY 和 WHERE 时,应该让 ORDER BY 位于 WHERE 之后。

    过滤数据

    filter condition 提取表数据的子集。

    可以通过

    • 关系运算 >=< 空值检查 IS NULL
    • 逻辑运算 AND NOT IN NOT 等

    来过滤数据。

    关键字 DISTINCT 关键字,指示数据库只返回不同的值。DISTINCT 关键字作用于所有的列。

    搜索数据

    通配符 wildcard:用来匹配值的一部分的特殊字符。

    搜索模式 search pattern:由字面值、通配符或两者组合构成的搜索条件。

    谓词 predicate:操作符何时不是操作符?答案是,它作为谓词时。从技术上说,LIKE 是谓词而不是操作符。虽然最终结果是相同的。

    常用的通配符有百分号 % 下划线 _ 方括号 [ ] 等。

    计算字段

    拼接字段,concat 就是一个函数

    SELECT
        Concat(
            vend_name,
            ' (',
            vend_country,
            ')'
        ) AS vend_title
    FROM
        Vendors
    ORDER BY
        vend_name;

     执行算术计算

    SELECT
        prod_id,
        quantity,
        item_price,
        quantity * item_price AS expanded_price
    FROM
        OrderItems
    WHERE
        order_num = 20008;

     其他算术运算符也可以使用。

    汇总数据

    首先讲讲函数,函数在多种编程语言里面皆有定义,SQL 中定义和它们差不多。

    函数主要分为文本处理函数、日期和时间处理函数、数值处理函数。重点是聚集函数。

    聚集函数 aggregate function:对某些行运行的函数,计算并返回一个值。常用的有:

    • AVG 求平均值,例如:SELECT AVG(prod_price) AS avg_price FROM Products;
    • COUNT 计数,例如:SELECT COUNT(*) AS num_cust FROM Customers;
    • MAX MIN 最大值和最小值,例如:SELECT MAX(prod_price) AS max_price FROM Products;
    • SUM 指定列的和,例如:SELECT SUM(quantity) AS items_ordered FROM OrderItems;

    上面这些函数可以组合使用。

    分组数据

    汇总表内容的子集。主要是 GROUP BY 子句和 HAVING 子句。

     例如:

    SELECT
        vend_id,
        COUNT(*) AS num_prods
    FROM
        Products
    GROUP BY
        vend_id;

    GROUP BY 子句指示 DBMS 分组数据,然后对每个组而不是整个结果集进行聚集。 

    关于 GROUP BY 的一些重要的规定。 

    一般用 HAVEING 子句过滤分组。HAVEING 分句非常类似于 WHERE。唯一的差别是,WHERE 过滤行,而 HAVING 过滤分组。二者句法是相同的。WHERE 在数据分组前进行过滤,HAVING 在数据分组后进行过滤。

    SELECT
        cust_id,
        COUNT(*) AS orders
    FROM
        Orders
    GROUP BY
        cust_id
    HAVING
        COUNT(*) >= 2;

     GROUP BY 和 ORDER BY 的组合使用。

    SELECT
        order_num,
        COUNT(*) AS items
    FROM
        OrderItems
    GROUP BY
        order_num
    HAVING
        COUNT(*) >= 3
    ORDER BY
        items,
        order_num;

    注意子句的顺序。 

    子查询

    子查询 subquery,即嵌套在其他查询中的查询。在 SELECT 语句中,子查询总是从内向外处理。

    SELECT cust_name, cust_contact
    FROM Customers
    WHERE cust_id IN (
        SELECT cust_id
        FROM orders
        WHERE order_num IN (
            SELECT order_num
            FROM OrderItems
            WHERE prod_id = 'RGAN01'
        )
    );

    作为计算字段使用子查询。

    SELECT cust_name, cust_state
        , (
            SELECT COUNT(*)
            FROM Orders
            WHERE Orders.cust_id = Customers.cust_id
        ) AS orders
    FROM Customers
    ORDER BY cust_name;

    以上是常见的子查询。 

    组合查询

    在数据查询中执行联结表 join。 

    笛卡儿积 cartesian product:由没有联结条件的表返回的结果为笛卡儿积。检索出的行的数目将是第一个表中的行数乘以第二个表中的行数。

    例如:SELECT vend_name, prod_name, prod_price FROM Vendors, Products;

    这样查询的结果一般不是我们想要的。

    内联结

    等值联结 equijoin:又称内联结 inner join,它基于两个表之间的相等测试。

    带条件的联结,这是简单语法

    SELECT vend_name, prod_name, prod_price
    FROM Vendors, Products
    WHERE Vendors.vend_id = Products.vend_id;

     带条件的联结,这是标准语法

    SELECT vend_name, prod_name, prod_price
    FROM Vendors
        INNER JOIN Products ON Vendors.vend_id = Products.vend_id;

    注意 inner join 可以多次使用连接多个表。 

    SELECT prod_name, vend_name, prod_price, quantity
    FROM Products 
    INNER JOIN Vendors ON Products.vend_id = Vendors.vend_id
    INNER JOIN OrderItems ON OrderItems.prod_id = Products.prod_id
    WHERE order_num = 20007;

     联结多个表

    SELECT prod_name, vend_name, prod_price, quantity
    FROM OrderItems, Products, Vendors
    WHERE (Products.vend_id = Vendors.vend_id
        AND OrderItems.prod_id = Products.prod_id
        AND order_num = 20007);

    表别名:表别名只能在查询执行中使用。与列别名不一样,表别名不返回到客户端。

    自联结

    self-join 

    SELECT c1.cust_id, c1.cust_name, c1.cust_contact
    FROM Customers c1, Customers c2
    WHERE c1.cust_name = c2.cust_name
        AND c2.cust_contact = 'Jim Jones';

     许多 DBMS 处理联结远比处理子查询快得多。

    自然联结

    natural join

    SELECT C.*, O.order_num, O.order_date, OI.prod_id, OI.quantity
        , OI.item_price
    FROM Customers C, Orders O, OrderItems OI
    WHERE (C.cust_id = O.cust_id
        AND OI.order_num = O.order_num
        AND prod_id = 'RGAN01');

     无论何时对表进行联结,应该至少有一列不止出现在一个表中(被联结的列)。标准的联结返回所有数据,相同的列甚至多次出现。自然联结排除多次出现,使每一列只返回一次。

    外联结

    outer join

    这是左联结

    SELECT Customers.cust_id, Orders.order_num
    FROM Customers
        LEFT JOIN Orders ON Customers.cust_id = Orders.cust_id;

     这是右联结

    SELECT Customers.cust_id, Orders.order_num
    FROM Customers
        RIGHT JOIN Orders ON Orders.cust_id = Customers.cust_id;

     许多联结将一个表中的行与另一个表中的行相关联,但有时候需要包含没有关联行的那些行。

    利用 UNION,可以把多条查询的结果作为一条组合查询返回。

    内联结是两张表中具有数据对应时才会产生一行记录。外联结则是以主表为准根据附表产生对应的记录。

    插入更新删除数据

    插入数据

    INSERT INTO Customers (cust_id, cust_name, cust_address, cust_city, cust_state
        , cust_zip, cust_country, cust_contact, cust_email)
    VALUES ('1000000006', 'Toy Land', '123 Any Street', 'New York', 'NY'
        , '11111', 'USA', NULL, NULL);

     插入检索出的数据

    INSERT INTO Customers (cust_id, cust_contact, cust_email, cust_name, cust_address
        , cust_city, cust_state, cust_zip, cust_country)
    SELECT cust_id, cust_contact, cust_email, cust_name, cust_address
        , cust_city, cust_state, cust_zip, cust_country
    FROM CustNew;

    上面的 INSERT SELECT 中 SELECT 语句可以包含 WHERE 子句,以过滤插入的数据。

    INSERT 通常只插入一行。要插入多行,必须执行多个 INSERT 语句。INSERT SELECT 是个例外,它可以用一条 INSERT 插入多行,不管 SELECT 语句返回多少行,都将被 INSERT 插入。

    从一个表复制到另一个表

    CREATE TABLE CustCopy AS
    SELECT * FROM Customers;

     更新数据

    UPDATE customers
    SET cust_email = 'kim@thetoystore.com'
    WHERE cust_id = '1000000005';

     删除数据

    DELETE FROM Customers
    WHERE cust_id = '1000000006';

    视图

    视图是虚拟的表。与包含数据的表不一样,视图只包含使用时动态检索数据的查询。

    因为视图不包含数据,所以每次使用视图时,都必须处理查询执行时需要的所有检索。如果你用多个联结和过滤创建了复杂的视图或者嵌套了视图,性能可能会下降得很厉害。因此,在部署使用了大量视图的应用前,应该进行测试。

    创建视图

    CREATE VIEW ProductCustomers
    AS
    SELECT cust_name, cust_contact, prod_id
    FROM Customers, Orders, OrderItems
    WHERE Customers.cust_id = Orders.cust_id
        AND OrderItems.order_num = Orders.order_num;

    视图的查询和普通的 SELECT 语句一样。

    存储过程

    存储过程就是为以后使用而保存的一条或多条 SQL 语句。可将其视为批文件,虽然它们的作用不仅限于批处理。 

    事务处理

    使用事务处理 transaction processing,通过确保成批的 SQL 操作要么完全操作,要么完全不执行,来维护数据库的完整性。

    事务处理相关的术语:

    • 事务 transaction 指一组 SQL 语句;
    • 回退 rollback 指撤销指定 SQL 语句的过程;
    • 提交 commit 指将未存储的 SQL 语句结果写入数据库表;
    • 保留点 savepoint 指事务处理中设置的临时占位符 placeholder,可以对它发布回退(与回退整个事物处理不同)。

    事务处理用来管理 INSERT UPDATE DELETE 语句。

    游标

    游标 cursor 是一个存储在 DBMS 服务器上的数据库查询,它不是一条 SELECT 语句,而是被该语句检索出来的结果集。在存储了游标之后,应用程序可以根据需要滚动或浏览其中的数据。

    有时,需要在检索出来的行中前进或后退一行或多行,这就是游标的用途所在。

    高级 SQL 特性

    约束

    约束 constraint:管理如何插入或处理数据库的规则。

    主键 primary key:是一种特殊的约束,用来保证一列(或一组列)中的值是唯一的,而且永不改动。

    外键是表中的一列,其值必须列在另一表的主键中。外键是保证引用完整性的极其重要的部分。

    唯一约束 UNIQUE 可以用于限制某一列的值不重复。

    检查约束用来保证一列(或一组列)中的数据满足一组指定的条件:

    • 检查最小或最大值。例如,防止 0 个物品的订单;
    • 指定范围。例如,保证发货日期大于等于今天的日期;
    • 只允许特定的值。

    索引

    创建索引

    CREATE INDEX prod_name_ind ON PRODUCTS (prod_name);

    触发器 

    触发器是特殊的存储过程,它在特定的数据库活动发生时自动执行。触发器可以与特定表上的 INSERT UPDATE DELETE 相关联。

    综合查询:

    显示所有的库:show database;

    使用名为 test 的库:use test;

    显示库中所有的表:show tables;

    显示表的所有信息:describe pet; 

    参考:

    mysql 官方文档

  • 相关阅读:
    python标准库
    python常用标准库
    django-restframework-serializers
    Resources.UnloadUnusedAssets
    Shader 的 Blend
    C++STL queue
    C++STL stack
    C++STL deque
    C++STL容器重点
    C++STL 迭代器
  • 原文地址:https://www.cnblogs.com/colin220/p/11060150.html
Copyright © 2011-2022 走看看