ODPS开发大全:入门篇(2)

本文涉及的产品
云原生大数据计算服务 MaxCompute,5000CU*H 100GB 3个月
云原生大数据计算服务MaxCompute,500CU*H 100GB 3个月
简介: ODPS开发大全:入门篇

 DQL


  • SELECT语句


1. SELECT语法


[with <cte>[, ...] ]SELECT [all | distinct] <SELECT_expr>[, <except_expr>][, <replace_expr>] ...       from <table_reference>       [where <where_condition>]       [group by {<col_list>|rollup(<col_list>)}]       [having <having_condition>]       [window <window_clause>]       [order by <order_condition>]       [distribute by <distribute_condition> [sort by <sort_condition>]|[ cluster by <cluster_condition>] ]       [limit <number>]


下面将介绍SELECT命令格式及如何实现嵌套查询、分组查询、排序等操作。


2. SELECT语序


--语法顺序from <table_reference>[where <where_condition>][group by <col_list>][having <having_condition>][window <window_name> AS (<window_definition>)][qualify <expression>]select [all | distinct] <select_expr>, <select_expr>, ...[order by <order_condition>][distribute by <distribute_condition> [sort by <sort_condition>] ][limit <number>]

场景1:from->where->group by->having->select->order by->limit

场景2:from->where->select->distribute by->sort by


3. WITH子句


with A as (SELECT 1 as C),B as (SELECT * from A) SELECT * from B;


在同一WITH子句中的CTE必须具有唯一的名字。

在WITH子句中定义的CTE仅对在同一WITH子句中的其他CTE可以使用。


4. 列表达式


------------------------------------------------------------------------------例子 --读取表xxxx_detail的列shop_nameSELECT xxxx_name from xxxx_detail;--查询表xxxx_detail中region列数据,如果有重复值时仅显示一条。SELECT distinct region from xxxx_detail;--选出xxxx_detail表中列名不为xxxx_name的所有列SELECT `(xxxx_name)?+.+` from xxxx_detail;--去重多列时,distinct的作用域是SELECT的列集合,不是单个列。SELECT distinct region, xxxx_date from xxxx_detail;


用列名指定要读取的列。

用星号(*)代表查询所有的列。

可以使用正则表达式。

在选取的列名前可以使用distinct去掉重复字段,只返回去重后的值。


5. 排除列


--读取xxxx_detail表的数据,并排除region列的数据。------------------------------------------------------------------------------例子SELECT * except(region) from xxxx_detail;


当希望读取表内大多数列的数据,同时要排除表中少数列的数据时。

表示读取表数据时会排除指定列(col1、col2)的数据。


6. WHERE


--配合关系运算符,筛选满足指定条件的数据。关系运算符包含:  >、<、=、>=、<=、<>  like、rlike  in、not in  between…and------------------------------------------------------------------------------例子SELECT * from xxxx_detailwhere xxxx_date >= '2008' and xxxx_date <= '2014';--等价于如下语句。SELECT * from xxxx_detail where xxxx_date between '2008' and '2014';


where子句为过滤条件。如果表是分区表,可以实现列裁剪。


7. GROUP BY


------------------------------------------------------------------------------例子
--直接使用输入表列名region作为group by的列,即以region值分组SELECT region from xxxx_detail group by region;
--以region值分组,返回每一组的销售额总量。SELECT sum(xxxx_price) from xxxx_detail group by region;
--以region值分组,返回每一组的region值(组内唯一)及销售额总量。SELECT region, sum (xxxx_price) from xxxx_detail group by region;


group by操作优先级高于SELECT操作,因此group by的取值是SELECT输入表的列名或由输入表的列构成的表达式。需要注意的是:

group by取值为正则表达式时,必须使用列的完整表达式。

SELECT语句中没有使用聚合函数的列必须出现在GROUP BY中。


8. HAVING


------------------------------------------------------------------------------例子--为直观展示数据呈现效果,向sale_detail表中追加数据。insert into sale_detail partition (sale_date='2014', region='shanghai')   values ('null','c5',null),('s6','c6',100.4),('s7','c7',100.5);--使用having子句配合聚合函数实现过滤。SELECT region,sum(total_price) from sale_detail group by region having sum(total_price)<305;


通常HAVING子句与聚合函数一起使用,实现过滤。


9. ORDER BY



------------------------------------------------------------------------------例子
--查询表xxxx_detail的信息,并按照xxxx_price升序排列前2条。SELECT * from xxxx_detail order by xxxx_price limit 2;
--将表xxx_detail按照xxxx_price升序排序后,输出从第3行开始的3行数据。SELECT xxxx_id,xxxx_price from xxxx_detail order by xxxx_price limit 3 offset 2;


默认对数据进行升序排序,如果降序排序,需要使用desc关键字。

order by默认要求带limit数据行数限制,没有limit会返回报错。


10. DISTRIBUTE BY哈希分片


------------------------------------------------------------------------------例子
--查询表xxxx_detail中的列region值并按照region值进行哈希分片。SELECT region from xxxx_detail distribute by region;--等价于如下语句。SELECT region as r from xxxx_detail distribute by region;SELECT region as r from xxxx_detail distribute by r;


distribute by控制Map(读数据)的输出在Reducer中是如何划分的,如果不希望Reducer的内容存在重叠,或需要对同一分组的数据一起处理,可以使用distribute by来保证同组数据分发到同一个Reducer中。


11. SORT BY局部排序


------------------------------------------------------------------------------例子
--查询表xxxx_detail中的列region和xxxx_price的值并按照region值进行哈希分片,然后按照xxxx_price对哈希分片结果进行局部升序排序。SELECT region,xxxx_price from xxxx_detail distribute by region sort by xxxx_price;
--查询表xxxx_detail中的列region和xxxx_price的值并按照region值进行哈希分片,然后按照xxxx_price对哈希分片结果进行局部降序排序。SELECT region,xxxx_price from xxxx_detail distribute by region sort by xxxx_price desc;
--如果sort by语句前没有distribute by,sort by会对每个Reduce中的数据进行局部排序。SELECT region,xxxx_price from xxxx_detail sort by xxxx_price desc;


sort by默认对数据进行升序排序,如果降序排序,需要使用desc关键字。

如果sort by语句前有distribute by,sort by会对distribute by的结果按照指定的列进行排序。


12. LIMIT限制输出行数


SELECT * FROM xxxxx.xxxx_xxxx_xxxxWHERE ds = 20240520LIMIT 100;


limit 中的number是常数,用于限制输出行数,取值范围为int32位取值范围。


  • 子查询


1. 基础子查询



--格式1select <select_expr> from (<select_statement>) [<sq_alias_name>];
--格式2select (<select_statement>) from <table_name>;


普通查询操作的对象是目标表,但是查询的对象也可以是另一个select语句,这种查询为子查询。在from子句中,子查询可以被当作一张表,与其他表或子查询进行join操作。


2. IN SUBQUERY



--in subquery与left semi join用法类似--格式一select<select_expr1>from<table_name1>where<select_expr2>  in(select<select_expr3>from<table_name2>);--等效于leftsemijoin如下语句。select<select_expr1>from<table_name1><alias_name1>leftsemijoin<table_name2><alias_name2>  on<alias_name1>.<select_expr2>=<alias_name2>.<select_expr3>;
--格式二select<select_expr1>from<table_name1>where<select_expr2>  in(select<select_expr3>from<table_name2>where     <table_name1>.<col_name>=<table_name2>.<col_name>);
------------------------------------------------------------------------------例子set odps.sql.allow.fullscan=true;select * from xxxx_detail where xxxx_price in (select xxxx_price from shop);
set odps.sql.allow.fullscan=true;select * from xxxx_detail where xxxx_price   in (select xxxx_price from shop where xxxx_id = shop.xxxx_id);


select_expr1:必填。格式为col1_name, col2_name, 正则表达式,...,表示待查询的普通列、分区列或正则表达式。

table_name1、table_name2:必填。表的名称。

select_expr2、select_expr3:必填。表示table_name1和table_name2互相映射的列名。

col_name:必填。表的列名。


3. NOT IN SUBQUERY



--如果查询目标表的指定列名中有任意一行为NULL,则not in表达式值为NULL,导致where条件不成立,无数据返回select <select_expr1> from <table_name1> where <select_expr2> not in (select <select_expr2> from <table_name2>);--等效于left anti join如下语句。select <select_expr1> from <table_name1> <alias_name1>   left anti join <table_name2> <alias_name2> on <alias_name1>.<select_expr1> = <alias_name2>.<select_expr2>;
------------------------------------------------------------------------------例子--创建一张新表shop1并追加数据。create table shop1 as select xxxx_name,xxxx_id,xxxx_price from xxxx_detail;insert into shop1 values ('s8','c1',100.1);select * from shop1 where xxxx_name not in (select xxxx_name from xxxx_detail);
set odps.sql.allow.fullscan=true;select * from shop1 where xxxx_name not in (select xxxx_name from xxxx_detail where xxxx_id = shop1.xxxx_id);


select_expr1:必填。格式为col1_name, col2_name, 正则表达式,...,表示待查询的普通列、分区列或正则表达式。

table_name1、table_name2:必填。表的名称。

select_expr2、select_expr3:必填。表示table_name1和table_name2互相映射的列名。

col_name:必填。表的列名。


4. EXISTS SUBQUERY


--使用exists subquery时,当子查询中有至少一行数据时,返回True,否则返回False。select <select_expr> from <table_name1> where exists    (select <select_expr> from <table_name2>     where <table_name2_colname> = <table_name1>.<colname>   );
------------------------------------------------------------------------------例子set odps.sql.allow.fullscan=true;select * from xxxx_detail where exists (select * from shop where customer_id = xxxx_detail.xxxx_id);--等效于以下语句。select * from xxxx_detail a left semi join shop b on a.xxxx_id = b.xxxx_id;


select_expr:必填。格式为col1_name, col2_name, 正则表达式,...,表示待查询的普通列、分区列或正则表达式。

table_name1、table_name2:必填。表的名称。

col_name:必填。表的列名。


5. NOT EXISTS SUBQUERY



--当子查询中无数据时,返回True,否则返回Falseselect <select_expr> from <table_name1> where not exists     (select <select_expr> from <table_name2> where <table_name2_colname> = <table_name1>.<colname>);
------------------------------------------------------------------------------例子set odps.sql.allow.fullscan=true;select * from xxxx_detail where not exists (select * from shop where xxxx_name = xxxx_detail.xxxx_name);--等效于以下语句。select * from xxxx_detail a left anti join shop b on a.shop_name = b.xxxx_name;


select_expr:必填。格式为col1_name, col2_name, 正则表达式,...,表示待查询的普通列、分区列或正则表达式。

table_name1、table_name2:必填。表的名称。

col_name:必填。表的列名。


6. SCALAR SUBQUERY



--当子查询的输出结果为单行单列时,可以做为标量使用,即可以参与标量运算。select <select_expr> from <table_name1> where   (<select count(*) from <table_name2> where <table_name2_colname> = <table_name1>.<colname>)   <标量运算符> <scalar_value>;
------------------------------------------------------------------------------例子set odps.sql.allow.fullscan=true;select * from shop where   (select count(*) from xxxx_detail where xxxx_detail.xxxx_name = shop.xxxx_name) >= 1;


select_expr:必填。格式为col1_name, col2_name, 正则表达式。

table_name1、table_name2:必填。表的名称。

col_name:必填。表的列名。

标量运算符:必填。例如大于(>)、小于(<)、等于(=)。

scalar_value:必填。标量值


  • 交集,并集和补集


1. 交集



--取交集不去重。<select_statement1> intersect all <select_statement2>;--取交集并去重。intersect效果等同于intersect distinct。<select_statement1> intersect [distinct] <select_statement2>;
------------------------------------------------------------------------------例子select * from values (1, 2), (1, 2), (3, 4), (5, 6) t(a, b) intersect all select * from values (1, 2), (1, 2), (3, 4), (5, 7) t(a, b);--结果+------------+------------+| a          | b          |+------------+------------+| 1          | 2          || 3          | 4          |+------------+------------+

select_statement1、select_statement2:必填。

distinct:可选。对两个数据集取交集的结果去重。


2. 并集


--取并集不去重。<select_statement1> union all <select_statement2>;--取并集并去重。<select_statement1> union [distinct] <select_statement2>;
------------------------------------------------------------------------------例子select * from values (1, 2), (1, 2), (3, 4) t(a, b) union all select * from values (1, 2), (1, 4) t(a, b);--结果+------------+------------+| a          | b          |+------------+------------+| 1          | 2          || 1          | 2          || 3          | 4          || 1          | 2          || 1          | 4          |+------------+------------+


select_statement1、select_statement2:必填。select语句。

distinct:可选。对两个数据集取并集的结果去重。


3. 补集


--取补集不去重。<select_statement1> except all <select_statement2>;<select_statement1> minus all <select_statement2>;--取补集并去重。<select_statement1> except [distinct] <select_statement2>;<select_statement1> minus [distinct] <select_statement2>;
------------------------------------------------------------------------------例子select * from values (1, 2), (1, 2), (3, 4), (3, 4), (5, 6), (7, 8) t(a, b)except all select * from values (3, 4), (5, 6), (5, 6), (9, 10) t(a, b);--结果+------------+------------+| a          | b          |+------------+------------+| 1          | 2          || 1          | 2          || 3          | 4          || 7          | 8          |+------------+------------+


select_statement1、select_statement2:必填。select语句。

distinct:可选。对取补集的结果去重。

相关实践学习
基于MaxCompute的热门话题分析
本实验围绕社交用户发布的文章做了详尽的分析,通过分析能得到用户群体年龄分布,性别分布,地理位置分布,以及热门话题的热度。
SaaS 模式云数据仓库必修课
本课程由阿里云开发者社区和阿里云大数据团队共同出品,是SaaS模式云原生数据仓库领导者MaxCompute核心课程。本课程由阿里云资深产品和技术专家们从概念到方法,从场景到实践,体系化的将阿里巴巴飞天大数据平台10多年的经过验证的方法与实践深入浅出的讲给开发者们。帮助大数据开发者快速了解并掌握SaaS模式的云原生的数据仓库,助力开发者学习了解先进的技术栈,并能在实际业务中敏捷的进行大数据分析,赋能企业业务。 通过本课程可以了解SaaS模式云原生数据仓库领导者MaxCompute核心功能及典型适用场景,可应用MaxCompute实现数仓搭建,快速进行大数据分析。适合大数据工程师、大数据分析师 大量数据需要处理、存储和管理,需要搭建数据仓库?学它! 没有足够人员和经验来运维大数据平台,不想自建IDC买机器,需要免运维的大数据平台?会SQL就等于会大数据?学它! 想知道大数据用得对不对,想用更少的钱得到持续演进的数仓能力?获得极致弹性的计算资源和更好的性能,以及持续保护数据安全的生产环境?学它! 想要获得灵活的分析能力,快速洞察数据规律特征?想要兼得数据湖的灵活性与数据仓库的成长性?学它! 出品人:阿里云大数据产品及研发团队专家 产品 MaxCompute 官网 https://www.aliyun.com/product/odps&nbsp;
相关文章
|
1天前
|
SQL 分布式计算 DataWorks
DataWorks产品使用合集之如何开发ODPS Spark任务
DataWorks作为一站式的数据开发与治理平台,提供了从数据采集、清洗、开发、调度、服务化、质量监控到安全管理的全套解决方案,帮助企业构建高效、规范、安全的大数据处理体系。以下是对DataWorks产品使用合集的概述,涵盖数据处理的各个环节。
|
1天前
|
数据可视化
Echarts数据可视化开发| 智慧数据平台
Echarts数据可视化开发| 智慧数据平台
|
1天前
|
数据可视化
Echarts数据可视化大屏开发| 大数据分析平台
Echarts数据可视化大屏开发| 大数据分析平台
|
26天前
|
存储 分布式计算 MaxCompute
构建NLP 开发问题之如何支持其他存储介质(如 HDFS、ODPS Volumn)在 transformers 框架中
构建NLP 开发问题之如何支持其他存储介质(如 HDFS、ODPS Volumn)在 transformers 框架中
|
4天前
|
分布式计算 大数据 Java
Scala 入门指南:从零开始的大数据开发
Scala 入门指南:从零开始的大数据开发
|
23天前
|
存储 SQL 机器学习/深度学习
阿里云数加大数据计算服务MaxCompute学习路线图:从入门到精通
将所学知识应用于实际工作中并不断进行实践和创新是提升技术能力的关键所在。用户可以结合业务需求和技术发展趋势积极探索新的应用场景和解决方案,并在实践中不断总结经验和教训以提升自己的技术水平和实践能力。
|
26天前
|
分布式计算 自然语言处理 MaxCompute
构建NLP 开发问题之如何在数据加载框架中实现从两个ODPS表中分别读取正样本和负样本,并在batch内以1:1的方式混合
构建NLP 开发问题之如何在数据加载框架中实现从两个ODPS表中分别读取正样本和负样本,并在batch内以1:1的方式混合
|
1天前
|
分布式计算 DataWorks 关系型数据库
DataWorks产品使用合集之ODPS数据怎么Merge到MySQL数据库
DataWorks作为一站式的数据开发与治理平台,提供了从数据采集、清洗、开发、调度、服务化、质量监控到安全管理的全套解决方案,帮助企业构建高效、规范、安全的大数据处理体系。以下是对DataWorks产品使用合集的概述,涵盖数据处理的各个环节。
|
6天前
|
消息中间件 数据采集 JSON
大数据 - DWD&DIM 行为数据
大数据 - DWD&DIM 行为数据
19 1
|
13天前
|
机器学习/深度学习 人工智能 分布式计算
理解并利用大数据的力量:解锁数据背后的价值
【8月更文挑战第7天】大数据已成为推动社会进步和经济发展的重要力量。通过理解并利用大数据的力量,企业可以解锁数据背后的价值,优化业务流程、提升决策效率和创新能力。然而,大数据应用也面临着诸多挑战和风险,需要企业不断学习和实践以应对。相信在未来的发展中,大数据将为我们带来更多的惊喜和机遇。

热门文章

最新文章