据我所理解;
排序方式排序仅在减速
为了通过全球订单的事情,但猛推万事成一个减速器
通过智能集群通过关键字hash分配到的东西减速并进行排序
所以我的问题是没有担保集群中的全球秩序? 通过看跌期权相同的密钥相同的进减速但对于相邻的键分布?
我可以找到关于这个问题的唯一文件是在这里 ,并从例如现在看来似乎全球订单他们。 但是,自定义我觉得它并不总是这样。
据我所理解;
排序方式排序仅在减速
为了通过全球订单的事情,但猛推万事成一个减速器
通过智能集群通过关键字hash分配到的东西减速并进行排序
所以我的问题是没有担保集群中的全球秩序? 通过看跌期权相同的密钥相同的进减速但对于相邻的键分布?
我可以找到关于这个问题的唯一文件是在这里 ,并从例如现在看来似乎全球订单他们。 但是,自定义我觉得它并不总是这样。
更短的回答:是的, CLUSTER BY
保证全局顺序,只要你愿意加入多个输出文件自己。
较长的版本:
ORDER BY x
:保证整体排序,但只通过一个减速推动所有资料,并参考。 这对于大的数据集基本上是不可接受的。 你最终一个排序的文件作为输出。 SORT BY x
:在每个N减速器的订单数据,但每个减速器可以接收重叠数据的范围。 你结束了N或范围重叠的多个排序的文件。 DISTRIBUTE BY x
:确保每个N减速器得到的非重叠的范围x
,但每个减速机的输出不进行排序。 你结束了N或与非重叠范围更未分类文件。 CLUSTER BY x
:确保每个N减速器通过在减速器那些范围变得不重叠的范围,然后排序。 这使您全局排序,并且是一样的做( DISTRIBUTE BY x
和SORT BY x
)。 你结束了N或与非重叠范围更加有序的文件。 合理? 所以CLUSTER BY
,基本上是更具可扩展性的版本ORDER BY
。
首先我想澄清: clustered by
只有你的钥匙分配到不同的桶, clustered by ... sorted by
分类GET桶。
用一个简单的实验(见下文),你可以看到,你不会在默认情况下得到的全球秩序。 其原因是,默认的分区分割使用的哈希码键,无论实际的键排序的。
但是你可以得到你的数据完全有序。
动机是“Hadoop的:权威指南”由汤姆·怀特(第3版,第8章,第274,总排序。),在那里他讨论TotalOrderPartitioner。
我先回答你的问题TotalOrdering,然后描述,我做了几样相关的蜂巢实验。
请记住:什么我描述这里是一个“概念验证”,我能够处理使用Claudera的CDH3分布的单一实例。
本来我希望org.apache.hadoop.mapred.lib.TotalOrderPartitioner会做的伎俩。 遗憾的是它并没有因为它看起来像按值蜂房分区,没有密钥。 所以我给它打上补丁(应该有子类,但我没有时间为):
更换
public int getPartition(K key, V value, int numPartitions) {
return partitions.findPartition(key);
}
同
public int getPartition(K key, V value, int numPartitions) {
return partitions.findPartition(value);
}
现在,您可以设置(修补)TotalOrderPartitioner为您的蜂巢分区:
hive> set hive.mapred.partitioner=org.apache.hadoop.mapred.lib.TotalOrderPartitioner;
hive> set total.order.partitioner.natural.order=false
hive> set total.order.partitioner.path=/user/yevgen/out_data2
我也用
hive> set hive.enforce.bucketing = true;
hive> set mapred.reduce.tasks=4;
在我的测试。
文件out_data2告诉TotalOrderPartitioner如何桶值。 您可以通过采样数据生成out_data2。 在我的测试我用从0 4个水桶和键10。我生成out_data2使用自组织的方法:
import org.apache.hadoop.util.ToolRunner;
import org.apache.hadoop.util.Tool;
import org.apache.hadoop.conf.Configured;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.io.NullWritable;
import org.apache.hadoop.io.SequenceFile;
import org.apache.hadoop.hive.ql.io.HiveKey;
import org.apache.hadoop.fs.FileSystem;
public class TotalPartitioner extends Configured implements Tool{
public static void main(String[] args) throws Exception{
ToolRunner.run(new TotalPartitioner(), args);
}
@Override
public int run(String[] args) throws Exception {
Path partFile = new Path("/home/yevgen/out_data2");
FileSystem fs = FileSystem.getLocal(getConf());
HiveKey key = new HiveKey();
NullWritable value = NullWritable.get();
SequenceFile.Writer writer = SequenceFile.createWriter(fs, getConf(), partFile, HiveKey.class, NullWritable.class);
key.set( new byte[]{1,3}, 0, 2);//partition at 3; 1 came from Hive -- do not know why
writer.append(key, value);
key.set( new byte[]{1, 6}, 0, 2);//partition at 6
writer.append(key, value);
key.set( new byte[]{1, 9}, 0, 2);//partition at 9
writer.append(key, value);
writer.close();
return 0;
}
}
然后我复制所得out_data2到HDFS(进入/用户/叶夫根·/ out_data2)
通过这些设置,我有我的数据分时段/排序(见我的实验列表中最后一个项目)。
这里是我的实验。
创建示例数据
的bash>回波-e “1 \ N3 \ N 2 \ N4 \ N5 \ N7 \ N6 \ n8 \ N9 \ N0”> data.txt中
创建基本的测试表:
蜂房>创建表测试(X INT); 蜂房>载荷数据的本地INPATH“的data.txt”到台试验;
基本上,这表包含从0到9的值,而无需顺序。
演示表复制如何工作的(真mapred.reduce.tasks参数其中规定的reduce任务最大数量使用)
蜂房>创建表TEST2(X INT);
蜂房>集mapred.reduce.tasks = 4;
蜂房>插入重写表TEST2从测试选择斧联接上AX = BX试验B; - stupied加入强制非平凡的map-reduce
的bash> hadoop的FS -cat /用户/蜂巢/仓库/ TEST2 / 000001_0
1
五
9
演示桶装。 你可以看到,密钥随机assinged没有任何排序顺序:
蜂房>创建由簇表TEST3(X INT)(X)转换成4桶;
蜂房>设置hive.enforce.bucketing = TRUE;
蜂房>插入重写表TEST3 SELECT * FROM测试;
的bash> hadoop的FS -cat /用户/蜂巢/仓库/ TEST3 / 000000_0
4
8
0
与分拣了瓢泼大雨。 结果是部分排序,不能完全排序
蜂房>创建由簇表TEST4(X INT)(X)用(x降序)分类成4桶;
蜂房>插入重写表TEST4 SELECT * FROM测试;
的bash> hadoop的FS -cat /用户/蜂巢/仓库/ TEST4 / 000001_0
1
五
9
你可以看到,值按升序排序。 貌似在CDH3蜂巢错误吗?
通过声明无群集入门部分进行排序:
蜂房>创建表TEST5从测试作为选择x通过X降序排序X分发;
的bash> hadoop的FS -cat /用户/蜂巢/仓库/ TEST5 / 000001_0
9
五
1
用我的修补TotalOrderParitioner:
蜂房>设置hive.mapred.partitioner = org.apache.hadoop.mapred.lib.TotalOrderPartitioner;
蜂房>设置total.order.partitioner.natural.order =假
蜂房>设置total.order.partitioner.path = /用户/训练/ out_data2
蜂房>创建由簇表TEST6(X INT)(x)的排序方法(X)转换成4桶;
蜂房>插入重写表TEST6 SELECT * FROM测试;
的bash> hadoop的FS -cat /用户/蜂巢/仓库/ TEST6 / 000000_0
1
2
0
的bash> hadoop的FS -cat /用户/蜂巢/仓库/ TEST6 / 000001_0
3
4
五
的bash> hadoop的FS -cat /用户/蜂巢/仓库/ TEST6 / 000002_0
7
6
8
的bash> hadoop的FS -cat /用户/蜂巢/仓库/ TEST6 / 000003_0
9
CLUSTER BY不会产生全局排序。
接受的答案(由拉斯Yencken)通过,说明该减速器将接收非重叠范围误导。 作为安东Zaviriukhin正确地指向BucketedTables文档,CLUSTER BY基本上DISTRIBUTE BY(同桶装)加排序每个桶/减速器内。 和分发通过简单的哈希和MODS到水桶,而散列函数可以 ,散列值的mod没有维持秩序(如果我>Ĵ我的哈希> j的哈希值)。
下面是示出重叠范围一个更好的例子
http://myitlearnings.com/bucketing-in-hive/
据我了解,简短的回答是不。你会得到重叠的范围。
从SortBy文档 :“群集通过是一条捷径两种分发由和排序。” “用相同的所有行分发由列将转到同一减速。” 但通过担保非重叠范围分发的信息。
而且,从DDL BucketedTables文档 :“如何配置单元穿过桶分配的行通常,铲斗数量由表达式hash_function(bucketing_column)MOD num_buckets来确定。” 我想,集群在Select语句使用相同的原理来减速器之间分配行,因为它的主要用途是用于填充时段的表格与数据。
我创建的表1个整数列“A”,并插入数字从0到9那里。
然后我设置减速器的编号,以2 set mapred.reduce.tasks = 2;
。
而select
从该表的数据Cluster by
条款select * from my_tab cluster by a;
而接收到的结果,我希望:
0
2
4
6
8
1
3
5
7
9
因此,首先减速机(编号为0)得到偶数(因为他们的模式2给出了0)
和第二减速器(数1)有奇数(因为它们的模式2给出1)
这就是如何“分发由”作品。
然后在“排序”排序每个机内部的结果。
集群由每减速排序不是全球性的。 在许多书籍也被错误或混淆提及。 它得到了在那里说你每个部门的员工姓名每个部门分配给特定的减速,然后排序,不ABT部门的为了照顾没有使用集群通过它更进行蚂蚁作为工作量减速器之间分配特定用途。
SortBy:N或范围重叠的多个排序的文件。
排序依据:单路输出,即完全有序。
分发由:分发通过保护每个N减速器获取列不重叠的范围,但各减速机的输出不进行排序。
欲了解更多信息http://commandstech.com/hive-sortby-vs-orderby-vs-distributeby-vs-clusterby/
ClusterBy:如上指同一例子,如果我们使用群集用X,这两个减速将进一步排序x行:
使用案例:当有一个大的数据集,然后一个应该去排序中排序,所有设定减速数据一起泡吧之前内部排序和增强的性能。 当由命令,因为所有的数据是通过一个单一的减速器,这增加了负荷,因此需要较长的时间来执行查询被传为较大的数据集的性能降低。 请看下面的例子11节点集群。
这一个是排序输出示例
这一个是排序示例输出
这一个是集群举例
我观察到,的数字排序,通过集群和分发由是相同的 ,但内部机制是不同的。 在DISTRIBUTE BY:同列的行会去一个减速,如。 DISTRIBUTE BY(市) - 班加罗尔的数据在一列中,德里数据在一个减速机: