Apache Tajo - SQL查询

本章介绍以下重要查询.

  • 谓词

  • 解释

  • 加入

让我们继续并执行查询.

谓词

谓词是一个表达式,用于计算真/假值和UNKNOWN.谓词用于WHERE子句和HAVING子句的搜索条件以及需要布尔值的其他构造.

IN谓词

确定是否要测试的表达式的值与子查询或列表中的任何值匹配.子查询是一个普通的SELECT语句,其结果集包含一列和一行或多行.此列或列表中的所有表达式必须与要测试的表达式具有相同的数据类型.

语法

IN::= 
<expression to test> [NOT] IN (<subquery>) 
| (<expression1>,...)

查询

select id,name,address from mytable where id in(2,3,4);

结果

上述查询将产生以下结果.

id,  name,   address 
------------------------------- 
2,  Amit,  12 old street 
3,  Bob,   10 cross street 
4,  David, 15 express avenue

查询从 mytable 返回学生ID 2,3和4的记录.

查询

select id,name,address from mytable where id not in(2,3,4);

结果

上述查询将产生以下结果.

id,  name,  address 
------------------------------- 
1,  Adam,   23 new street 
5,  Esha,   20 garden street 
6,  Ganga,  25 north street 
7,  Jack,   2 park street 
8,  Leena,  24 south street 
9,  Mary,   5 west street 
10, Peter,  16 park avenue

以上查询返回 mytable 中的记录,其中学生不在2,3和4中.

喜欢谓词

LIKE谓词比较第一个表达式中指定的字符串,用于计算字符串值,该值被称为要测试的值,使用在第二个表达式中定义的用于计算字符串值的模式.

模式可以包含任何通配符的组合,例如 :

  • 下划线符号(_),其中可以用来代替任何要测试的值中的单个字符.

  • 百分号(%),它替换要测试的值中的任何零个或多个字符的字符串.

语法

LIKE::= 
<expression for calculating the string value> 
[NOT] LIKE 
<expression for calculating the string value> 
[ESCAPE <symbol>]

查询

select * from mytable where name like ‘A%';

结果

上述查询将产生以下结果.

id,  name,  address,     age,  mark 
------------------------------- 
1,  Adam,  23 new street,  12,  90 
2,  Amit,  12 old street,  13,  95

查询返回名称以"A"开头的学生的mytable记录.

查询

select * from mytable where name like ‘_a%';

结果

上述查询将产生以下结果.

id,  name,  address,    age,  mark 
——————————————————————————————————————- 
4,  David,  15 express avenue,  12,  85 
6,  Ganga,  25 north street,    12,  55 
7,  Jack,  2 park street,       12,  60 
9,  Mary,  5 west street,       12,  75

查询返回来自 mytable 的学生,其姓名以'a'开头作为第二个字符.

在搜索条件中使用NULL值

现在让我们了解如何在搜索条件中使用NULL值.

语法

Predicate  
IS [NOT] NULL

查询

select name from mytable where name is not null;

结果

上述查询将产生以下结果.

name 
------------------------------- 
Adam 
Amit 
Bob 
David 
Esha 
Ganga 
Jack 
Leena 
Mary 
Peter  
(10 rows, 0.076 sec, 163 B selected)

这里,结果为true所以它返回表中的所有名称.

查询

现在让我们以NULL条件检查查询.

default> select name from mytable where name is null;

结果

上述查询将产生以下结果.

name 
------------------------------- 
(0 rows, 0.068 sec, 0 B selected)

解释

Explain 用于获取查询执行计划.它显示了一个语句的逻辑和全局计划执行.

逻辑计划查询

explain select * from mytable;  
explain 
-------------------------------  
   => target list: default.mytable.id (INT4), default.mytable.name (TEXT), 
      default.mytable.address (TEXT), default.mytable.age (INT4), default.mytable.mark (INT4) 
   
   => out schema: {
   (5) default.mytable.id (INT4), default.mytable.name (TEXT), default.mytable.address (TEXT), 
      default.mytable.age (INT4), default.mytable.mark (INT4)
   } 
   
   => in schema: {
	(5) default.mytable.id (INT4), default.mytable.name (TEXT), default.mytable.address (TEXT), 
      default.mytable.age (INT4), default.mytable.mark (INT4)
   }

结果

上述查询将产生以下结果.

Explain

查询结果显示给定表的逻辑计划格式.逻辑计划返回以下三个结果 :

  • 目标列表

  • Out schema

  • 在架构中

全局计划查询

explain global select * from mytable;  
explain 
------------------------------- 
------------------------------------------------------------------------------- 
Execution Block Graph (TERMINAL - eb_0000000000000_0000_000002) 
------------------------------------------------------------------------------- 
|-eb_0000000000000_0000_000002 
   |-eb_0000000000000_0000_000001 
------------------------------------------------------------------------------- 
Order of Execution 
------------------------------------------------------------------------------- 
1: eb_0000000000000_0000_000001 
2: eb_0000000000000_0000_000002 
-------------------------------------------------------------------------------  
======================================================= 
Block Id: eb_0000000000000_0000_000001 [ROOT] 
=======================================================  
SCAN(0) on default.mytable 
   
   => target list: default.mytable.id (INT4), default.mytable.name (TEXT), 
      default.mytable.address (TEXT), default.mytable.age (INT4), default.mytable.mark (INT4) 
   
   => out schema: {
	(5) default.mytable.id (INT4), default.mytable.name (TEXT),default.mytable.address (TEXT), 
      default.mytable.age (INT4), default.mytable.mark (INT4)
   } 
   
   => in schema: {
	(5) default.mytable.id (INT4), default.mytable.name (TEXT), default.mytable.address (TEXT), 
      default.mytable.age (INT4), default.mytable.mark (INT4)
   }  
======================================================= 
Block Id: eb_0000000000000_0000_000002 [TERMINAL] 
======================================================= 
(24 rows, 0.065 sec, 0 B selected)

结果

上述查询将生成以下结果.

全球计划

此处,全球计划显示执行块ID,执行顺序及其信息.

连接

SQL连接用于组合来自两个或多个表的行.以下是不同类型的SQL连接和减号;

  • 内部连接

  • {LEFT |对... | FULL}外部加入

  • 交叉加入

  • 自我加入

  • 自然加入

考虑以下两个表来执行连接操作.

表1  - 客户

Id名称地址年龄
1 客户123 Old Street21
2 客户212新街23
3 客户310 Express Avenue22
4 客户415 Express Avenue22
5 客户520 Garden Street33
6 客户621 North Street25

表2  -  customer_order

Id订单IDEmp Id
1 1101
2 2102
3 3103
4 4104
5 5105

让我们现在继续并对上面两个表执行SQL连接操作.

内部连接

当两个表中的列匹配时,Inner连接选择两个表中的所有行.

语法

SELECT column_name(s) FROM table1 INNER JOIN table2 ON table1.column_name = table2.column_name;

查询

default> select c.age,c1.empid from customers c inner join customer_order c1 on c.id = c1.id;

结果

上述查询将产生以下结果.

age,  empid 
------------------------------- 
21,  101 
23,  102 
22,  103 
22,  104 
33,  105

查询匹配两个表中的五行.因此,它返回第一个表中匹配的行年龄.

左外连接

左外连接保留所有行的"留下"表格,无论是否在"右"表上都有匹配的行.

查询

select c.name,c1.empid from customers c left outer join customer_order c1 on c.id = c1.id;

结果

上述查询将产生以下结果.

name,       empid 
------------------------------- 
customer1,  101 
customer2,  102 
customer3,  103 
customer4,  104 
customer5,  105 
customer6,

这里,左外连接返回customer(左)表中的name列行和customer_order(右)表中empid列匹配的行.

右外连接

右外连接保留"右"表的所有行,无论"左"表中是否有匹配的行.

查询

select c.name,c1.empid from customers c right outer join customer_order c1 on c.id = c1.id;

结果

上述查询将产生以下结果.

name,      empid 
------------------------------- 
customer1,  101 
customer2,  102 
customer3,  103 
customer4,  104 
customer5,  105

此处,Right Outer Join从customer_order(右)表返回empid行,name列匹配customers表中的行.

Full Outer Join

Full Outer Join保留左右表中的所有行.

查询

select * from customers c full outer join customer_order c1 on c.id = c1.id;

结果

上述查询将产生以下结果.

Full Outer Join

查询返回两者中所有匹配和不匹配的行customers和customer_order表.

交叉连接

这将返回两个或多个连接表中记录集的笛卡尔积.

语法

SELECT *  FROM table1  CROSS JOIN table2;

查询

select orderid,name,address from customers,customer_order;

结果

上述查询将产生以下结果.

交叉加入

上述查询返回表格的笛卡尔积.

自然加入

自然加入不使用任何比较运算符.它没有连接笛卡尔积的方式.只有在两个关系之间至少存在一个共同属性时,我们才能执行自然连接.

语法

SELECT * FROM table1 NATURAL JOIN table2;

查询

select * from customers natural join customer_order;

结果

上述查询将产生以下结果.

自然加入

这里,两个表之间存在一个公共列ID.使用该公共列,自然连接连接两个表.

自我加入

使用SQL SELF JOIN将表连接到自身,就像表是两个表一样,在SQL语句中暂时重命名至少一个表.

语法

SELECT a.column_name, b.column_name...  
FROM table1 a, table1 b  
WHERE a.common_filed = b.common_field

查询

default> select c.id,c1.name from customers c, customers c1 where c.id = c1.id;

结果

上述查询将产生以下结果.

id,   name 
------------------------------- 
1,   customer1 
2,   customer2 
3,   customer3 
4,   customer4 
5,   customer5 
6,   customer6

查询将客户表连接到自身.