SQL是一种编程语言,用于管理以表格形式(即表格)存储在关系数据库中的数据。关系数据库由许多相互关联的表组成。表之间的关系是在共享列的意义上形成的。有许多不同的关系数据库管理系统(例如MySQL、PostgreSQL、SQLServer)。它们可能使用略有不同的SQL语法。但是,两者之间的差异很小,因此如果您学会了如何使用其中一种,则可以轻松切换到另一种。在本文中,我们将介绍30个示例,涉及以下SQL操作:创建数据库和表将数据插入表中从表中删除数据更新表使用各种select语句查询表您的计算机或云端有很多替代使用SQL。我目前正在通过终端在Linux计算机上使用MySQL。另一种常见的替代方法是安装MySQLWorkbench。示例1我们首先从终端连接到MySQL服务器并创建一个数据库。~$sudomysql-uroot我们将被提示输入密码。我们现在连接到我们计算机中的MySQL服务器。以下命令创建一个名为“retail”的数据库。mysql>createdatabaseretail;mysql>useretail;我们不在还不包含任何表的零售数据库中。示例2我们将首先使用createtable命令创建一个名为“customer”的表。mysql>createtablecustomer(->cust_idintprimarykey,->ageint,->locationvarchar(20),->gendervarchar(20)->);我们在括号内定义列的名称和关联的数据类型。指定cust_id列作为主键。主键是唯一标识每一行的列。就像熊猫数据框的索引一样。示例3我们将创建第二个名为“Orders”的表。mysql>createtableorders(->order_idintprimarykey,->datedate,->amountdecimal(5,2),->cust_idint,->foreignkey(cust_id)referencescustomer(cust_id)->ondeletecascade->);一开始我们提到了关系表是通过共享列相互关联的。关联两个表的列是外键。外键是将一个表与另一个表相关联的东西。外键包含另一个表的主键。orders表中的cust_id列是一个外键,它将orders表与customers表相关联。我们在创建表时指定此条件。在最后一行,我们用短语“ondeletecascade”指定了另一个条件。它告诉MySQL在删除customer表中的行时要做什么。订单表中的每一行都属于一个客户。客户表中的每一行都包含一个唯一的客户ID并代表一个客户。如果删除客户表中的一行,则意味着我们不再有该客户。因此,属于该客户的订单不再具有关联的客户ID。“删除级联”意味着没有关联客户ID的订单也将被删除。实例4零售数据库现在包含两个表。我们可以使用showtable命令来查看数据库中存在的表。mysql>showtables;+----------------+|Tables_in_retail|+----------------+|客户||orders|+-----------------+注意:SQL中的订单以分号(“;”)结尾。示例5desc或describe命令从列名、数据类型和其他一些信息的角度对表进行汇总。mysql>descorders;+------------+------------+------+-----+---------+--------+|Field|Type|Null|Key|Default|Extra|+--------+-------------+------+-----+--------+--------+|order_id|int(11)|NO|PRI|NULL|||date|date|YES||NULL|||amount|decimal(5,2)|YES||NULL|||cust_id|int(11)|YES|MUL|NULL||+---------+------------+------+-----+--------+--------+例6我们可以修改现有表。例如,altertable命令可用于添加新列或删除现有列。让我们在订单表中添加一列“is_sale”。mysql>altertableordersaddis_salevarchar(20);我们写下列名和数据类型以及add关键字。mysql>descorders;+------------+------------+------+-----+---------+--------+|Field|Type|Null|Key|Default|Extra|+--------+-------------+------+-----+--------+--------+|order_id|int(11)|NO|PRI|NULL|||date|日期|是||NULL|||数量|十进制(5,2)|YES||NULL|||cust_id|int(11)|YES|MUL|NULL|||is_sale|varchar(20)|YES||NULL||+---------+-------------+-----+-----+--------+--------+i??s_sale列已添加到订单表中。实例7altertable也可用于删除语法略有变化的列。mysql>altertableordersdropis_sale;使用drop关键字而不是add关键字。我们也不必编写数据类型来删除列。示例8我们有表,但它们不包含任何数据。填充表的一种方法是插入语句。mysql>insertintocustomervalues(->1000,42,'Austin','female'->);指定的值以相同的顺序插入到列中。因此,我们需要保持顺序一致。示例9我们可以通过分隔每一行来同时插入多行。mysql>insertintocustomervalues->(1001,34,'Austin','male'),->(1002,37,'Houston','male'),->(1003,25,'Austin','female'),->(1004,28,'休斯顿','女'),->(1005,22,'达拉斯','男'),->;我添加了一些行并以相同的方式填充了订单。还有其他方法可以用数据填充表。例如,我们可以使用loaddatainfile或loaddatalocalinfile语句加载csv文件。示例10deletefrom语句可用于删除表中的现有行。我们需要通过提供条件来标识要删除的行。例如,下面的语句将删除订单ID为17的行。mysql>deletefromorders->whereorder_id=17;如果我们不指定条件,则删除给定表中的所有行。示例11我们还可以更新现有行。让我们更新订单表中的一行。+------------+------------+--------+--------+|order_id|date|amount|cust_id|+----------+------------+--------+--------+|1|2020-10-01|24.40|1001|+--------+------------+--------+---------+这是订单表中的第一行。我们想将订单金额更改为27.40。mysql>updateorders->setamount=27.40->whereorder_id=1;mysql>select*fromorderslimit1;+---------+------------+--------+--------+|order_id|date|amount|cust_id|+--------+------------+--------+--------+|1|2020-10-01|27.40|1001|+--------+------------+--------+--------+我们把更新后的值写在set关键字后面。通过在where关键字后提供条件来标识要更新的行。示例12如果要通过复制现有表的结构来创建表,可以使用带有like关键字的createtable语句。mysql>createtableorders_copylikeorders;mysql>showtables;+----------------+|Tables_in_retail|+------------------+|customer||orders||orders_copy|+----------------+orders_copy表与orders表具有相同的结构,但不包含任何数据。示例13我们还可以使用data通过将createtable与select语句一起使用来创建现有表的副本。mysql>createtablenew_orders->select*fromorders;似乎是两个独立语句的组合。第一行创建表,第二行用订单表中的数据填充表。Example14droptable语句可以用来删除数据库中的表。mysql>droptableorders_copy,new_orders;mysql>showtables;+----------------+|Tables_in_retail|+------------------+|customer||orders|+------------------+我们已经成功删除了在前面的例子中创建的表。我们在数据库中有两个关系表。以下示例将说明我们如何使用选择查询从这些表中检索数据。示例15最简单的查询是查看表中的所有列。mysql>select*fromorders->limit3;+------------+------------+--------+----------+|order_id|date|amount|cust_id|+----------+------------+--------+---------+|1|2020-10-01|27.40|1001||2|2020-10-01|36.20|1000||3|2020-10-01|65.45|1002|+----------+------------+--------+---------+"*"选择所有列,limit关键字强加一个对要显示的行数的限制。示例16通过写入列名而不是“*”,我们只能选择某些列。mysql>selectorder_id,amount->fromorders->limit3;+--------+--------+|order_id|amount|+----------+-------+|1|27.40||2|36.20||3|65.45|+--------+------+实例17我们可以使用子句指定要选择的行的条件。以下查询将返回2020–10–01的所有订单。mysql>select*fromorders->wheredate='2020-10-01';+----------+------------+--------+----------+|order_id|date|amount|cust_id|+----------+------------+-------+--------+|1|2020-10-01|27.40|1001||2|2020-10-01|36.20|1000||3|2020-10-01|65.45|1002|+--------+------------+--------+--------+例18wheresentenceaccepts多个条件。让我们在前面的示例中向查询添加另一个条件。mysql>select*fromorders->wheredate='2020-10-01'andamount>50;+----------+------------+--------+--------+|order_id|date|amount|cust_id|+--------+------------+--------+--------+|3|2020-10-01|65.45|1002|+--------+------------+--------+--------+例19我们可能希望对查询结果进行排序,这可以使用orderby子句来完成。以下查询将返回2020–10–02的订单并按金额排序。mysql>select*fromorders->wheredate='2020-10-02'->orderbyamount;+----------+------------+--------+--------+|order_id|date|amount|cust_id|+--------+------------+--------+--------+|5|2020-10-02|18.80|1005||6|2020-10-02|21.15|1009||4|2020-10-02|34.40|1001||7|2020-10-02|34.40|1008||8|2020-10-02|41.10|1002|+--------+------------+--------+----------+示例20默认情况下,orderby子句按升序对行进行排序。我们可以使用desc关键字将其更改为降序。mysql>select*fromorders->wheredate='2020-10-02'->orderbyamountdesc;+---------+------------+--------+--------+|order_id|date|amount|cust_id|+--------+------------+--------+--------+|8|2020-10-02|41.10|1002||4|2020-10-02|34.40|1001||7|2020-10-02|34.40|1008||6|2020-10-02|21.15|1009||5|2020-10-02|18.80|1005|+--------+------------+--------+----------+Instance21SQL是一种通用语言,也可以作为数据分析工具。它提供了许多函数来分析和转换从数据库中查询的数据。例如,我们可以计算订单表中的唯一天数。mysql>selectcount(distinct(date))asday_count->fromorders;+------------+|day_count|+------------+|4|+-----------+订单表包含4个不同日期的订单。“as”关键字用于重命名查询结果中的列。否则,列的名称将为“count(distinct(date))”。实例22在订单表中有4天。我们还可以找出每天有多少订单。groupby子句将帮助我们完成这项任务。mysql>selectdate,count(order_id)asorder_count->fromorders->groupbydate;+------------+------------+|日期|order_count|+----------+------------+|2020-10-01|3||2020-10-02|5||2020-10-03|6||2020-10-04|2|+------------+------------+我们计算订单并按日期列出分组。Example23我们将计算每天的平均订单金额,并将结果按照平均金额降序排列。mysql>selectdate,avg(amount)->fromorders->groupbydate->orderbyavg(amount)desc;+------------+------------+|日期|平均(金额)|+------------+------------+|2020-10-01|43.016667||2020-10-04|42.150000||2020-10-03|37.025000||2020-10-02|29.970000|+------------+------------+示例24我们要修改前面示例中的查询,只包括平均金额大于30的日期。mysql>selectdate,avg(amount)->fromorders->groupbydate->havingavg(amount)>30->orderbyavg(金额)desc;+------------+--------------+|date|avg(amount)|+------------+------------+|2020-10-01|43.016667||2020-10-04|42.150000||2020-10-03|37.025000|重要的是请注意,查询中语句的顺序很重要。例如,如果orderby子句放在having子句之前,就会产生错误。示例25我们想找出每天的最大订货量。mysql>selectdate,max(amount)->fromorders->groupbydate;+------------+------------+|date|max(amount)|+------------+------------+|2020-10-01|65.45||2020-10-02|41.10||2020-10-03|80.20||2020-10-04|50.10|Example26我们想在select语句中组合多个聚合函数。为了说明这一点,让我们详细说明前面的示例。我们想看看每个客户的最大订货量和最小订货量之间的差异。我们还想根据升序的差异对结果进行排序,并显示前三个结果。mysql>selectcust_id,max(amount)-min(amount)asdif->fromorders->groupbycust_id->orderbydifdesc->limit3;+--------+--------+|cust_id|dif|+--------+--------+|1007|46.00||1009|28.95||1002|24.35|+--------+-------+diff列是最大数量减去最小数量得到的。示例27现在我们切换到客户表。让我们看看每个城市有多少女性和男性顾客。我们需要在groupby子句中同时写入location和gender列。mysql>selectlocation,gender,count(cust_id)->fromcustomer->groupbylocation,gender;+--------+--------+----------------+|location|gender|count(cust_id)|+---------+------+--------------+|奥斯汀|女|2||奥斯汀|男|1||达拉斯|女|2||达拉斯|男|2||休斯顿|女|2||休斯顿|男|1|+----------+--------+----------------+例28客户表和订单表根据cust_id列相互关联。我们可以使用SQL连接从两个表中查询数据。我们想在客户表中查看每个城市的平均订单价值。mysql>selectcustomer.location,avg(orders.amount)asavg->fromcustomer->joinorders->oncustomer.cust_id=orders.cust_id->groupbycustomer.location;+----------+----------+|location|avg|+--------+----------+|奥斯汀|33.333333||达拉斯|34.591667||休斯顿|44.450000|+----------+------------+因为我们从两个不同的表中选择列,关联的表名将用于指定列名。上面查询的第二、第三和第四行根据每个表中的cust_id列将客户表和订单表连接在一起。请注意,列名不必相同。无论我们使用“on”关键字提供什么列名,都将根据这些列进行比较或匹配。示例29我们想查看在2020-10-03下订单的客户的平均年龄。mysql>selectavg(c.age)asavg_age->fromcustomerc->joinorderso->onc.cust_id=o.cust_id->whereo.date='2020-10-03';+---------+|avg_age|+--------+|30.0000|+--------+我们还可以为表名使用别名。当我们需要多次输入表名时,它就派上用场了。示例30我们想查看订单量最大的客户所在的位置。mysql>selectc.location,o.amount->fromcustomerc->joinorderso->onc.cust_id=o.cust_id->whereo.amount=(selectmax(amount)fromorders)->;+----------+--------+|位置|数量|+--------+------+|达拉斯|80.20|+---------+--------+在此查询中,我们有一个嵌套的选择语句。金额条件是使用订单表中单独的选择语句计算的。这个任务可以通过其他方式完成。我选择这种方法来介绍嵌套查询的概念。结论我相信本文中的30个示例将全面介绍SQL。我们讨论了以下主题:创建具有关系表的数据库修改表将数据插入表中从表中删除数据编写查询以从表中检索数据当然,可以使用SQL完成更高级的查询和操作。熟悉基础知识后,最好继续进行更高级的操作。原文链接:https://towardsdatascience.com/30-examples-to-master-sql-c8004705479a
