当前位置: 首页 > news >正文

板凳-------Mysql cookbook学习 (十一--------11)

14.4 从表中消除重复项 7/14/2025 9:19:12 PM

mysql> select * from catalog_list order by last_name, first_name;
+-----------+-------------+--------------------------+
| last_name | first_name  | street                   |
+-----------+-------------+--------------------------+
| Baxter    | Wallace     | 57 3rd Ave.              |
| BAXTER    | WALLACE     | 57 3rd Ave.              |
| Baxter    | Wallace     | 57 3rd Ave., Apt 102     |
| Baxter    | Wallace     | 57 3rd Ave.              |
| BAXTER    | WALLACE     | 57 3rd Ave.              |
| Baxter    | Wallace     | 57 3rd Ave., Apt 102     |
| Brown     | Bartholomew | 432 River Run            |
| Brown     | Bartholomew | 432 River Run            |
| Isaacson  | Jim         | 515 Fordam St., Apt. 917 |
| Isaacson  | Jim         | 515 Fordam St., Apt. 917 |
| McTavish  | Taylor      | 432 River Run            |
| McTavish  | Taylor      | 432 River Run            |
| Pinter    | Marlene     | 9 Sunset Trail           |
| Pinter    | Marlene     | 9 Sunset Trail           |
| Pinter    | Marlene     | 9 Sunset Trail           |
| Pinter    | Marlene     | 9 Sunset Trail           |
+-----------+-------------+--------------------------+
16 rows in set (0.00 sec)mysql> create table tmpp7 like catalog_list;
Query OK, 0 rows affected (0.08 sec)mysql> insert into tmpp7 select distinct * from catalog_list;
Query OK, 6 rows affected (0.01 sec)
Records: 6  Duplicates: 0  Warnings: 0mysql> select * from tmpp7 order by last_name, first_name;
+-----------+-------------+--------------------------+
| last_name | first_name  | street                   |
+-----------+-------------+--------------------------+
| Baxter    | Wallace     | 57 3rd Ave.              |
| Baxter    | Wallace     | 57 3rd Ave., Apt 102     |
| Brown     | Bartholomew | 432 River Run            |
| Isaacson  | Jim         | 515 Fordam St., Apt. 917 |
| McTavish  | Taylor      | 432 River Run            |
| Pinter    | Marlene     | 9 Sunset Trail           |
+-----------+-------------+--------------------------+
6 rows in set (0.00 sec)mysql> drop table catalog_list;
Query OK, 0 rows affected (0.04 sec)mysql> rename table tmpp7 to catalog_list;
Query OK, 0 rows affected (0.04 sec)mysql> create table tmpp7 like catalog_list;
Query OK, 0 rows affected (0.06 sec)mysql> alter table tmpp7 add primary key (last_name, first_name);
Query OK, 0 rows affected (0.12 sec)
Records: 0  Duplicates: 0  Warnings: 0mysql> insert ignore into tmpp7 select * from catalog_list;
Query OK, 5 rows affected, 1 warning (0.01 sec)
Records: 6  Duplicates: 1  Warnings: 1mysql> select * from tmpp7 order by last_name, first_name;
+-----------+-------------+--------------------------+
| last_name | first_name  | street                   |
+-----------+-------------+--------------------------+
| Baxter    | Wallace     | 57 3rd Ave.              |
| Brown     | Bartholomew | 432 River Run            |
| Isaacson  | Jim         | 515 Fordam St., Apt. 917 |
| McTavish  | Taylor      | 432 River Run            |
| Pinter    | Marlene     | 9 Sunset Trail           |
+-----------+-------------+--------------------------+
5 rows in set (0.00 sec)mysql> drop table catalog_list;
Query OK, 0 rows affected (0.03 sec)mysql> rename table tmpp7 to catalog_list;
Query OK, 0 rows affected (0.03 sec)

14.5 从自连接的结果中消除重复

mysql> select year(s1.statehood) as year,-> s1.name as name1, s1.statehood as statehood1,-> s2.name as name2, s2.statehood as statehood2-> from states as s1 inner join states as s2-> on year(s1.statehood) = year(s2.statehood) and s1.name = s2.name-> order by year, s1.name, s2.name;
+------+----------------+------------+----------------+------------+
| year | name1          | statehood1 | name2          | statehood2 |
+------+----------------+------------+----------------+------------+
| 1787 | Delaware       | 1787-12-07 | Delaware       | 1787-12-07 |
| 1787 | New Jersey     | 1787-12-18 | New Jersey     | 1787-12-18 |
| 1787 | Pennsylvania   | 1787-12-12 | Pennsylvania   | 1787-12-12 |
| 1788 | Connecticut    | 1788-01-09 | Connecticut    | 1788-01-09 |
| 1788 | Georgia        | 1788-01-02 | Georgia        | 1788-01-02 |
| 1788 | Maryland       | 1788-04-28 | Maryland       | 1788-04-28 |
| 1788 | Massachusetts  | 1788-02-06 | Massachusetts  | 1788-02-06 |
| 1788 | New Hampshire  | 1788-06-21 | New Hampshire  | 1788-06-21 |
| 1788 | New York       | 1788-07-26 | New York       | 1788-07-26 |
| 1788 | South Carolina | 1788-05-23 | South Carolina | 1788-05-23 |
| 1788 | Virginia       | 1788-06-25 | Virginia       | 1788-06-25 |
| 1789 | North Carolina | 1789-11-21 | North Carolina | 1789-11-21 |
| 1790 | Rhode Island   | 1790-05-29 | Rhode Island   | 1790-05-29 |
| 1791 | Vermont        | 1791-03-04 | Vermont        | 1791-03-04 |
| 1792 | Kentucky       | 1792-06-01 | Kentucky       | 1792-06-01 |
| 1796 | Tennessee      | 1796-06-01 | Tennessee      | 1796-06-01 |
| 1803 | Ohio           | 1803-03-01 | Ohio           | 1803-03-01 |
| 1812 | Louisiana      | 1812-04-30 | Louisiana      | 1812-04-30 |
| 1816 | Indiana        | 1816-12-11 | Indiana        | 1816-12-11 |
| 1817 | Mississippi    | 1817-12-10 | Mississippi    | 1817-12-10 |
| 1818 | Illinois       | 1818-12-03 | Illinois       | 1818-12-03 |
| 1819 | Alabama        | 1819-12-14 | Alabama        | 1819-12-14 |
| 1820 | Maine          | 1820-03-15 | Maine          | 1820-03-15 |
| 1821 | Missouri       | 1821-08-10 | Missouri       | 1821-08-10 |
| 1836 | Arkansas       | 1836-06-15 | Arkansas       | 1836-06-15 |
| 1837 | Michigan       | 1837-01-26 | Michigan       | 1837-01-26 |
| 1845 | Florida        | 1845-03-03 | Florida        | 1845-03-03 |
| 1845 | Texas          | 1845-12-29 | Texas          | 1845-12-29 |
| 1846 | Iowa           | 1846-12-28 | Iowa           | 1846-12-28 |
| 1848 | Wisconsin      | 1848-05-29 | Wisconsin      | 1848-05-29 |
| 1850 | California     | 1850-09-09 | California     | 1850-09-09 |
| 1858 | Minnesota      | 1858-05-11 | Minnesota      | 1858-05-11 |
| 1859 | Oregon         | 1859-02-14 | Oregon         | 1859-02-14 |
| 1861 | Kansas         | 1861-01-29 | Kansas         | 1861-01-29 |
| 1863 | West Virginia  | 1863-06-20 | West Virginia  | 1863-06-20 |
| 1864 | Nevada         | 1864-10-31 | Nevada         | 1864-10-31 |
| 1867 | Nebraska       | 1867-03-01 | Nebraska       | 1867-03-01 |
| 1876 | Colorado       | 1876-08-01 | Colorado       | 1876-08-01 |
| 1889 | Montana        | 1889-11-08 | Montana        | 1889-11-08 |
| 1889 | North Dakota   | 1889-11-02 | North Dakota   | 1889-11-02 |
| 1889 | South Dakota   | 1889-11-02 | South Dakota   | 1889-11-02 |
| 1889 | Washington     | 1889-11-11 | Washington     | 1889-11-11 |
| 1890 | Idaho          | 1890-07-03 | Idaho          | 1890-07-03 |
| 1890 | Wyoming        | 1890-07-10 | Wyoming        | 1890-07-10 |
| 1896 | Utah           | 1896-01-04 | Utah           | 1896-01-04 |
| 1907 | Oklahoma       | 1907-11-16 | Oklahoma       | 1907-11-16 |
| 1912 | Arizona        | 1912-02-14 | Arizona        | 1912-02-14 |
| 1912 | New Mexico     | 1912-01-06 | New Mexico     | 1912-01-06 |
| 1959 | Alaska         | 1959-01-03 | Alaska         | 1959-01-03 |
| 1959 | Hawaii         | 1959-08-21 | Hawaii         | 1959-08-21 |
+------+----------------+------------+----------------+------------+
50 rows in set (0.01 sec)这个查询会:
1.	找出同一年加入联邦的州对
2.	按字母顺序排列每对州的名称(name1是字母顺序靠前的,name2是字母顺序靠后的)
3.	按照年份、name1和name2排序结果mysql> SELECT YEAR(s1.statehood) AS year,->        IF(s1.name < s2.name, s1.name, s2.name) AS name1,->        IF(s1.name < s2.name, s1.statehood, s2.statehood) AS statehood1,->        IF(s1.name < s2.name, s2.name, s1.name) AS name2,->        IF(s1.name < s2.name, s2.statehood, s1.statehood) AS statehood2-> FROM states AS s1-> INNER JOIN states AS s2-> ON YEAR(s1.statehood) = YEAR(s2.statehood) AND s1.name != s2.name-> ORDER BY year, name1, name2;
+------+----------------+------------+----------------+------------+
| year | name1          | statehood1 | name2          | statehood2 |
+------+----------------+------------+----------------+------------+
| 1787 | Delaware       | 1787-12-07 | New Jersey     | 1787-12-18 |
| 1787 | Delaware       | 1787-12-07 | New Jersey     | 1787-12-18 |
| 1787 | Delaware       | 1787-12-07 | Pennsylvania   | 1787-12-12 |
| 1787 | Delaware       | 1787-12-07 | Pennsylvania   | 1787-12-12 |
| 1787 | New Jersey     | 1787-12-18 | Pennsylvania   | 1787-12-12 |
| 1787 | New Jersey     | 1787-12-18 | Pennsylvania   | 1787-12-12 |
| 1788 | Connecticut    | 1788-01-09 | Georgia        | 1788-01-02 |
| 1788 | Connecticut    | 1788-01-09 | Georgia        | 1788-01-02 |
| 1788 | Connecticut    | 1788-01-09 | Maryland       | 1788-04-28 |
| 1788 | Connecticut    | 1788-01-09 | Maryland       | 1788-04-28 |
| 1788 | Connecticut    | 1788-01-09 | Massachusetts  | 1788-02-06 |
| 1788 | Connecticut    | 1788-01-09 | Massachusetts  | 1788-02-06 |
| 1788 | Connecticut    | 1788-01-09 | New Hampshire  | 1788-06-21 |
| 1788 | Connecticut    | 1788-01-09 | New Hampshire  | 1788-06-21 |
| 1788 | Connecticut    | 1788-01-09 | New York       | 1788-07-26 |
| 1788 | Connecticut    | 1788-01-09 | New York       | 1788-07-26 |
| 1788 | Connecticut    | 1788-01-09 | South Carolina | 1788-05-23 |
| 1788 | Connecticut    | 1788-01-09 | South Carolina | 1788-05-23 |
| 1788 | Connecticut    | 1788-01-09 | Virginia       | 1788-06-25 |
| 1788 | Connecticut    | 1788-01-09 | Virginia       | 1788-06-25 |
| 1788 | Georgia        | 1788-01-02 | Maryland       | 1788-04-28 |
| 1788 | Georgia        | 1788-01-02 | Maryland       | 1788-04-28 |
| 1788 | Georgia        | 1788-01-02 | Massachusetts  | 1788-02-06 |
| 1788 | Georgia        | 1788-01-02 | Massachusetts  | 1788-02-06 |
| 1788 | Georgia        | 1788-01-02 | New Hampshire  | 1788-06-21 |
| 1788 | Georgia        | 1788-01-02 | New Hampshire  | 1788-06-21 |
| 1788 | Georgia        | 1788-01-02 | New York       | 1788-07-26 |
| 1788 | Georgia        | 1788-01-02 | New York       | 1788-07-26 |
| 1788 | Georgia        | 1788-01-02 | South Carolina | 1788-05-23 |
| 1788 | Georgia        | 1788-01-02 | South Carolina | 1788-05-23 |
| 1788 | Georgia        | 1788-01-02 | Virginia       | 1788-06-25 |
| 1788 | Georgia        | 1788-01-02 | Virginia       | 1788-06-25 |
| 1788 | Maryland       | 1788-04-28 | Massachusetts  | 1788-02-06 |
| 1788 | Maryland       | 1788-04-28 | Massachusetts  | 1788-02-06 |
| 1788 | Maryland       | 1788-04-28 | New Hampshire  | 1788-06-21 |
| 1788 | Maryland       | 1788-04-28 | New Hampshire  | 1788-06-21 |
| 1788 | Maryland       | 1788-04-28 | New York       | 1788-07-26 |
| 1788 | Maryland       | 1788-04-28 | New York       | 1788-07-26 |
| 1788 | Maryland       | 1788-04-28 | South Carolina | 1788-05-23 |
| 1788 | Maryland       | 1788-04-28 | South Carolina | 1788-05-23 |
| 1788 | Maryland       | 1788-04-28 | Virginia       | 1788-06-25 |
| 1788 | Maryland       | 1788-04-28 | Virginia       | 1788-06-25 |
| 1788 | Massachusetts  | 1788-02-06 | New Hampshire  | 1788-06-21 |
| 1788 | Massachusetts  | 1788-02-06 | New Hampshire  | 1788-06-21 |
| 1788 | Massachusetts  | 1788-02-06 | New York       | 1788-07-26 |
| 1788 | Massachusetts  | 1788-02-06 | New York       | 1788-07-26 |
| 1788 | Massachusetts  | 1788-02-06 | South Carolina | 1788-05-23 |
| 1788 | Massachusetts  | 1788-02-06 | South Carolina | 1788-05-23 |
| 1788 | Massachusetts  | 1788-02-06 | Virginia       | 1788-06-25 |
| 1788 | Massachusetts  | 1788-02-06 | Virginia       | 1788-06-25 |
| 1788 | New Hampshire  | 1788-06-21 | New York       | 1788-07-26 |
| 1788 | New Hampshire  | 1788-06-21 | New York       | 1788-07-26 |
| 1788 | New Hampshire  | 1788-06-21 | South Carolina | 1788-05-23 |
| 1788 | New Hampshire  | 1788-06-21 | South Carolina | 1788-05-23 |
| 1788 | New Hampshire  | 1788-06-21 | Virginia       | 1788-06-25 |
| 1788 | New Hampshire  | 1788-06-21 | Virginia       | 1788-06-25 |
| 1788 | New York       | 1788-07-26 | South Carolina | 1788-05-23 |
| 1788 | New York       | 1788-07-26 | South Carolina | 1788-05-23 |
| 1788 | New York       | 1788-07-26 | Virginia       | 1788-06-25 |
| 1788 | New York       | 1788-07-26 | Virginia       | 1788-06-25 |
| 1788 | South Carolina | 1788-05-23 | Virginia       | 1788-06-25 |
| 1788 | South Carolina | 1788-05-23 | Virginia       | 1788-06-25 |
| 1845 | Florida        | 1845-03-03 | Texas          | 1845-12-29 |
| 1845 | Florida        | 1845-03-03 | Texas          | 1845-12-29 |
| 1889 | Montana        | 1889-11-08 | North Dakota   | 1889-11-02 |
| 1889 | Montana        | 1889-11-08 | North Dakota   | 1889-11-02 |
| 1889 | Montana        | 1889-11-08 | South Dakota   | 1889-11-02 |
| 1889 | Montana        | 1889-11-08 | South Dakota   | 1889-11-02 |
| 1889 | Montana        | 1889-11-08 | Washington     | 1889-11-11 |
| 1889 | Montana        | 1889-11-08 | Washington     | 1889-11-11 |
| 1889 | North Dakota   | 1889-11-02 | South Dakota   | 1889-11-02 |
| 1889 | North Dakota   | 1889-11-02 | South Dakota   | 1889-11-02 |
| 1889 | North Dakota   | 1889-11-02 | Washington     | 1889-11-11 |
| 1889 | North Dakota   | 1889-11-02 | Washington     | 1889-11-11 |
| 1889 | South Dakota   | 1889-11-02 | Washington     | 1889-11-11 |
| 1889 | South Dakota   | 1889-11-02 | Washington     | 1889-11-11 |
| 1890 | Idaho          | 1890-07-03 | Wyoming        | 1890-07-10 |
| 1890 | Idaho          | 1890-07-03 | Wyoming        | 1890-07-10 |
| 1912 | Arizona        | 1912-02-14 | New Mexico     | 1912-01-06 |
| 1912 | Arizona        | 1912-02-14 | New Mexico     | 1912-01-06 |
| 1959 | Alaska         | 1959-01-03 | Hawaii         | 1959-08-21 |
| 1959 | Alaska         | 1959-01-03 | Hawaii         | 1959-08-21 |
+------+----------------+------------+----------------+------------+
82 rows in set (0.00 sec)增加distinct 消除多余的拷贝
mysql> SELECT distinct YEAR(s1.statehood) AS year,->        IF(s1.name < s2.name, s1.name, s2.name) AS name1,->        IF(s1.name < s2.name, s1.statehood, s2.statehood) AS statehood1,->        IF(s1.name < s2.name, s2.name, s1.name) AS name2,->        IF(s1.name < s2.name, s2.statehood, s1.statehood) AS statehood2-> FROM states AS s1-> INNER JOIN states AS s2-> ON YEAR(s1.statehood) = YEAR(s2.statehood) AND s1.name != s2.name-> ORDER BY year, name1, name2;
+------+----------------+------------+----------------+------------+
| year | name1          | statehood1 | name2          | statehood2 |
+------+----------------+------------+----------------+------------+
| 1787 | Delaware       | 1787-12-07 | New Jersey     | 1787-12-18 |
| 1787 | Delaware       | 1787-12-07 | Pennsylvania   | 1787-12-12 |
| 1787 | New Jersey     | 1787-12-18 | Pennsylvania   | 1787-12-12 |
| 1788 | Connecticut    | 1788-01-09 | Georgia        | 1788-01-02 |
| 1788 | Connecticut    | 1788-01-09 | Maryland       | 1788-04-28 |
| 1788 | Connecticut    | 1788-01-09 | Massachusetts  | 1788-02-06 |
| 1788 | Connecticut    | 1788-01-09 | New Hampshire  | 1788-06-21 |
| 1788 | Connecticut    | 1788-01-09 | New York       | 1788-07-26 |
| 1788 | Connecticut    | 1788-01-09 | South Carolina | 1788-05-23 |
| 1788 | Connecticut    | 1788-01-09 | Virginia       | 1788-06-25 |
| 1788 | Georgia        | 1788-01-02 | Maryland       | 1788-04-28 |
| 1788 | Georgia        | 1788-01-02 | Massachusetts  | 1788-02-06 |
| 1788 | Georgia        | 1788-01-02 | New Hampshire  | 1788-06-21 |
| 1788 | Georgia        | 1788-01-02 | New York       | 1788-07-26 |
| 1788 | Georgia        | 1788-01-02 | South Carolina | 1788-05-23 |
| 1788 | Georgia        | 1788-01-02 | Virginia       | 1788-06-25 |
| 1788 | Maryland       | 1788-04-28 | Massachusetts  | 1788-02-06 |
| 1788 | Maryland       | 1788-04-28 | New Hampshire  | 1788-06-21 |
| 1788 | Maryland       | 1788-04-28 | New York       | 1788-07-26 |
| 1788 | Maryland       | 1788-04-28 | South Carolina | 1788-05-23 |
| 1788 | Maryland       | 1788-04-28 | Virginia       | 1788-06-25 |
| 1788 | Massachusetts  | 1788-02-06 | New Hampshire  | 1788-06-21 |
| 1788 | Massachusetts  | 1788-02-06 | New York       | 1788-07-26 |
| 1788 | Massachusetts  | 1788-02-06 | South Carolina | 1788-05-23 |
| 1788 | Massachusetts  | 1788-02-06 | Virginia       | 1788-06-25 |
| 1788 | New Hampshire  | 1788-06-21 | New York       | 1788-07-26 |
| 1788 | New Hampshire  | 1788-06-21 | South Carolina | 1788-05-23 |
| 1788 | New Hampshire  | 1788-06-21 | Virginia       | 1788-06-25 |
| 1788 | New York       | 1788-07-26 | South Carolina | 1788-05-23 |
| 1788 | New York       | 1788-07-26 | Virginia       | 1788-06-25 |
| 1788 | South Carolina | 1788-05-23 | Virginia       | 1788-06-25 |
| 1845 | Florida        | 1845-03-03 | Texas          | 1845-12-29 |
| 1889 | Montana        | 1889-11-08 | North Dakota   | 1889-11-02 |
| 1889 | Montana        | 1889-11-08 | South Dakota   | 1889-11-02 |
| 1889 | Montana        | 1889-11-08 | Washington     | 1889-11-11 |
| 1889 | North Dakota   | 1889-11-02 | South Dakota   | 1889-11-02 |
| 1889 | North Dakota   | 1889-11-02 | Washington     | 1889-11-11 |
| 1889 | South Dakota   | 1889-11-02 | Washington     | 1889-11-11 |
| 1890 | Idaho          | 1890-07-03 | Wyoming        | 1890-07-10 |
| 1912 | Arizona        | 1912-02-14 | New Mexico     | 1912-01-06 |
| 1959 | Alaska         | 1959-01-03 | Hawaii         | 1959-08-21 |
+------+----------------+------------+----------------+------------+
41 rows in set (0.00 sec)mysql> SELECT YEAR(s1.statehood) AS year,->        IF(s1.name < s2.name, s1.name, s2.name) AS name1,->        IF(s1.name < s2.name, s1.statehood, s2.statehood) AS statehood1,->        IF(s1.name < s2.name, s2.name, s1.name) AS name2,->        IF(s1.name < s2.name, s2.statehood, s1.statehood) AS statehood2-> FROM states AS s1-> INNER JOIN states AS s2-> ON YEAR(s1.statehood) = YEAR(s2.statehood) AND s1.name < s2.name-> ORDER BY year, name1, name2;
+------+----------------+------------+----------------+------------+
| year | name1          | statehood1 | name2          | statehood2 |
+------+----------------+------------+----------------+------------+
| 1787 | Delaware       | 1787-12-07 | New Jersey     | 1787-12-18 |
| 1787 | Delaware       | 1787-12-07 | Pennsylvania   | 1787-12-12 |
| 1787 | New Jersey     | 1787-12-18 | Pennsylvania   | 1787-12-12 |
| 1788 | Connecticut    | 1788-01-09 | Georgia        | 1788-01-02 |
| 1788 | Connecticut    | 1788-01-09 | Maryland       | 1788-04-28 |
| 1788 | Connecticut    | 1788-01-09 | Massachusetts  | 1788-02-06 |
| 1788 | Connecticut    | 1788-01-09 | New Hampshire  | 1788-06-21 |
| 1788 | Connecticut    | 1788-01-09 | New York       | 1788-07-26 |
| 1788 | Connecticut    | 1788-01-09 | South Carolina | 1788-05-23 |
| 1788 | Connecticut    | 1788-01-09 | Virginia       | 1788-06-25 |
| 1788 | Georgia        | 1788-01-02 | Maryland       | 1788-04-28 |
| 1788 | Georgia        | 1788-01-02 | Massachusetts  | 1788-02-06 |
| 1788 | Georgia        | 1788-01-02 | New Hampshire  | 1788-06-21 |
| 1788 | Georgia        | 1788-01-02 | New York       | 1788-07-26 |
| 1788 | Georgia        | 1788-01-02 | South Carolina | 1788-05-23 |
| 1788 | Georgia        | 1788-01-02 | Virginia       | 1788-06-25 |
| 1788 | Maryland       | 1788-04-28 | Massachusetts  | 1788-02-06 |
| 1788 | Maryland       | 1788-04-28 | New Hampshire  | 1788-06-21 |
| 1788 | Maryland       | 1788-04-28 | New York       | 1788-07-26 |
| 1788 | Maryland       | 1788-04-28 | South Carolina | 1788-05-23 |
| 1788 | Maryland       | 1788-04-28 | Virginia       | 1788-06-25 |
| 1788 | Massachusetts  | 1788-02-06 | New Hampshire  | 1788-06-21 |
| 1788 | Massachusetts  | 1788-02-06 | New York       | 1788-07-26 |
| 1788 | Massachusetts  | 1788-02-06 | South Carolina | 1788-05-23 |
| 1788 | Massachusetts  | 1788-02-06 | Virginia       | 1788-06-25 |
| 1788 | New Hampshire  | 1788-06-21 | New York       | 1788-07-26 |
| 1788 | New Hampshire  | 1788-06-21 | South Carolina | 1788-05-23 |
| 1788 | New Hampshire  | 1788-06-21 | Virginia       | 1788-06-25 |
| 1788 | New York       | 1788-07-26 | South Carolina | 1788-05-23 |
| 1788 | New York       | 1788-07-26 | Virginia       | 1788-06-25 |
| 1788 | South Carolina | 1788-05-23 | Virginia       | 1788-06-25 |
| 1845 | Florida        | 1845-03-03 | Texas          | 1845-12-29 |
| 1889 | Montana        | 1889-11-08 | North Dakota   | 1889-11-02 |
| 1889 | Montana        | 1889-11-08 | South Dakota   | 1889-11-02 |
| 1889 | Montana        | 1889-11-08 | Washington     | 1889-11-11 |
| 1889 | North Dakota   | 1889-11-02 | South Dakota   | 1889-11-02 |
| 1889 | North Dakota   | 1889-11-02 | Washington     | 1889-11-11 |
| 1889 | South Dakota   | 1889-11-02 | Washington     | 1889-11-11 |
| 1890 | Idaho          | 1890-07-03 | Wyoming        | 1890-07-10 |
| 1912 | Arizona        | 1912-02-14 | New Mexico     | 1912-01-06 |
| 1959 | Alaska         | 1959-01-03 | Hawaii         | 1959-08-21 |
+------+----------------+------------+----------------+------------+
41 rows in set (0.00 sec)

第15章:执行事务
15.0 引言

mysql> CREATE TABLE pilot (->   pilot_id INT PRIMARY KEY,->   name VARCHAR(50),->   available ENUM('yes','no')-> );
Query OK, 0 rows affected (0.05 sec)mysql> select @p_val := pilot_id from pilot where available = 'yes' limit 1;
Empty set, 1 warning (0.00 sec)mysql> update pilot set available = 'no' where pilot_id = @p_val;
Query OK, 0 rows affected (0.00 sec)
Rows matched: 0  Changed: 0  Warnings: 0mysql> update flight set pilot_id = @p_val where flight_id = 578;
ERROR 1146 (42S02): Table 'cookbook.flight' doesn't exist
mysql> INSERT INTO pilot (pilot_id, name, available) VALUES-> (1, 'John Smith', 'yes'),-> (2, 'Jane Doe', 'yes'),-> (3, 'Mike Johnson', 'no');
Query OK, 3 rows affected (0.01 sec)
Records: 3  Duplicates: 0  Warnings: 0mysql> SELECT @p_val := pilot_id FROM pilot WHERE available = 'yes' LIMIT 1;
+--------------------+
| @p_val := pilot_id |
+--------------------+
|                  1 |
+--------------------+
1 row in set, 1 warning (0.00 sec)mysql> CREATE TABLE flight (->   flight_id INT PRIMARY KEY,->   pilot_id INT,->   flight_date DATETIME,->   -- 其他需要的列->   FOREIGN KEY (pilot_id) REFERENCES pilot(pilot_id)-> );
Query OK, 0 rows affected (0.09 sec)mysql>
mysql> -- 插入测试数据
mysql> INSERT INTO flight (flight_id, pilot_id, flight_date) VALUES-> (578, NULL, '2023-12-01 10:00:00');
Query OK, 1 row affected (0.01 sec)

15.1 使用事务存储引擎

mysql> show engines\g
+--------------------+---------+----------------------------------------------------------------+--------------+------+------------+
| Engine             | Support | Comment                                                        | Transactions | XA   | Savepoints |
+--------------------+---------+----------------------------------------------------------------+--------------+------+------------+
| MEMORY             | YES     | Hash based, stored in memory, useful for temporary tables      | NO           | NO   | NO         |
| MRG_MYISAM         | YES     | Collection of identical MyISAM tables                          | NO           | NO   | NO         |
| CSV                | YES     | CSV storage engine                                             | NO           | NO   | NO         |
| FEDERATED          | YES     | Federated MySQL storage engine                                 | NO           | NO   | NO         |
| PERFORMANCE_SCHEMA | YES     | Performance Schema                                             | NO           | NO   | NO         |
| MyISAM             | YES     | MyISAM storage engine                                          | NO           | NO   | NO         |
| InnoDB             | DEFAULT | Supports transactions, row-level locking, and foreign keys     | YES          | YES  | YES        |
| ndbinfo            | NO      | MySQL Cluster system information storage engine                | NULL         | NULL | NULL       |
| BLACKHOLE          | YES     | /dev/null storage engine (anything you write to it disappears) | NO           | NO   | NO         |
| ARCHIVE            | YES     | Archive storage engine                                         | NO           | NO   | NO         |
| ndbcluster         | NO      | Clustered, fault-tolerant tables                               | NULL         | NULL | NULL       |
+--------------------+---------+----------------------------------------------------------------+--------------+------+------------+
11 rows in set (0.00 sec)mysql> create table ttt1 (i int) engine = InnoDB;
Query OK, 0 rows affected (0.05 sec)mysql> create table ttt2 (i int) engine = BDB;
ERROR 1286 (42000): Unknown storage engine 'BDB'
mysql> create table ttt2 (i int) engine = MyISAM;
Query OK, 0 rows affected (0.02 sec)mysql> alter table ttt engine = InnoDB;
Query OK, 0 rows affected (0.26 sec)
Records: 0  Duplicates: 0  Warnings: 0

15.2 使用sql执行事务

mysql> DROP TABLE ttt;
Query OK, 0 rows affected (0.04 sec)mysql> CREATE TABLE ttt (i INT) ENGINE = InnoDB;
Query OK, 0 rows affected (0.06 sec)mysql> START TRANSACTION;
Query OK, 0 rows affected (0.00 sec)mysql> INSERT INTO ttt (i) VALUES(1);
Query OK, 1 row affected (0.00 sec)mysql> COMMIT;
Query OK, 0 rows affected (0.01 sec)mysql>  INSERT INTO ttt (i) VALUES(2);
Query OK, 1 row affected (0.01 sec)mysql> commit;
Query OK, 0 rows affected (0.00 sec)mysql> select * from ttt;
+------+
| i    |
+------+
|    1 |
|    2 |
+------+
2 rows in set (0.00 sec)mysql> insert into ttt (x) values(3);
ERROR 1054 (42S22): Unknown column 'x' in 'field list'
mysql> rollback;
Query OK, 0 rows affected (0.00 sec)mysql> select * from ttt;
+------+
| i    |
+------+
|    1 |
|    2 |
+------+
2 rows in set (0.00 sec)mysql> set autocommit = 0;
Query OK, 0 rows affected (0.00 sec)
•	作用:关闭自动提交模式(默认是 autocommit=1,即每条SQL语句自动提交)
•	效果:后续所有操作将在一个事务中,直到显式执行 COMMITROLLBACK
•	类比:相当于打开了一个"编辑会话",所有修改不会立即生效mysql> insert into ttt (i) values(3);
Query OK, 1 row affected (0.00 sec)mysql> insert into ttt (i) values(4);
Query OK, 1 row affected (0.00 sec)mysql> commit;
Query OK, 0 rows affected (0.01 sec)mysql> select * from ttt;
+------+
| i    |
+------+
|    1 |
|    2 |
|    3 |
|    4 |
+------+
4 rows in set (0.00 sec)mysql> set autocommit = 1;
Query OK, 0 rows affected (0.00 sec)
•	作用:重新开启自动提交模式
•	后续影响:
o	每条SQL语句将再次自动成为独立事务
o	不需要显式执行 COMMIT在 MySQL 中,执行 DROP DATABASE 后无法通过 ROLLBACK 恢复数据库,这是由以下几个关键原因决定的:
1. DDL 语句的自动提交特性
•	所有 DDL(数据定义语言)语句(如 CREATE, ALTER, DROP)会自动提交当前事务,不受 autocommit 设置影响。
•	即使你设置了 SET autocommit=0,执行 DROP DATABASE 时:
sql
复制
下载
SET autocommit=0;
DROP DATABASE mydb;  -- 这条语句会立即提交
ROLLBACK;           -- 此时已无效
2. 事务日志不记录 DDL 操作
•	事务的回滚依赖于事务日志(undo log),但 DDL 操作:
o	直接修改数据字典(元数据)
o	不生成可回滚的事务日志
o	会隐式提交当前所有未提交的事务
3. 物理文件删除
•	DROP DATABASE 不仅删除元数据,还会直接删除磁盘上的数据文件(.ibd, .frm 等)
•	这种物理删除操作超出了事务系统的管理范围
对比示例
操作类型	是否可回滚	原因
INSERT/UPDATE	✅ 可以	生成 undo log,事务系统可回滚
DROP DATABASE	❌ 不可以	自动提交+无 undo log+物理文件删除
解决方案(如果误删数据库)
1.	从备份恢复:
bash
复制
下载
mysql -u root -p < backup.sql
2.	使用二进制日志(需提前开启):
sql
复制
下载
mysqlbinlog --start-datetime="2023-11-01 00:00:00" binlog.000123 | mysql -u root -p
3.	专业数据恢复工具(如 Percona Data Recovery Tool for InnoDB)
预防措施
sql
复制
下载
-- 重要操作前先备份
CREATE DATABASE mydb_backup;
USE mydb_backup;
CREATE TABLE ... SELECT * FROM original_db.*;  -- 快速克隆-- 或使用 mysqldump
mysqldump -u root -p original_db > backup.sql
总结:DROP DATABASE 是设计上不可逆的操作,因其直接修改物理存储结构,这与事务系统的设计目标(管理数据修改而非结构变更)有本质区别。
http://www.lryc.cn/news/588688.html

相关文章:

  • 使用 Java 获取 PDF 页面信息(页数、尺寸、旋转角度、方向、标签与边框)
  • PySpark Standalone 集群
  • PySpark 常用算子详解
  • Java使用itextpdf7生成pdf文档
  • 【开源】一款基于 .NET 和 Vue3 开源(Apache)的MES管理系统,您的新一代工厂管理助手!
  • 【雅思播客016】New Year Resolution 新年决心
  • Luban配置教程
  • CSS :root伪类详解:实现动态主题切换的关键所在
  • 从浏览器到服务器:TCP 段的网络传输之旅
  • 建筑兔零基础人工智能自学记录109|LangChain简单翻译应用-19
  • Linux 基础 IO
  • 手机当路由,连接机器人和电脑
  • Java实现word、pdf转html保留格式
  • JavaScript与Vue:现代前端开发的完美组合
  • Spark Expression codegen
  • Swift实现股票图:从基础到高级
  • 线程(一) linux
  • 使用Dify+fastmcp 实现mcp服务,内含详细步骤与源码
  • Mac IDEA启动报错:Error occurred during initialization of VM
  • Twisted study notes[1]
  • [附源码+数据库+毕业论文+开题报告]基于Spring+MyBatis+MySQL+Maven+jsp实现的车辆运输管理系统,推荐!
  • etcd自动压缩清理
  • easy-ui中的相对路径和绝对路径问题
  • 现代CSS实战:用变量与嵌套重构可维护的前端样式
  • 【GPIO】从STM32F103入门GPIO寄存器
  • 腿姐政治笔记唯物辩证法(2)(12356)
  • 面试遇到的问题
  • 使用JS编写用户信息采集表单
  • 利用android studio,对图片资源进行二次压缩
  • 网络编程-epoll模型/udp通信