一、hbase架构简介

  • Zookeeper:作为分布式的协调。RegionServer也会把自己的信息写到ZooKeeper中。
  • HDFS是Hbase运行的底层文件系统。
  • RegionServer,理解为数据节点,存储数据的。
  • Master :RegionServer要实时的向Master报告信息。Master知道全局的RegionServer运行情况,可以控制RegionServer的故障转移和Region的切分。

架构的细分

  • HMaster是Master Server的实现,负责监控集群中的RegionServer实例,同时所有metadata改变的接口,在集群中,通常运行在NameNode上面。

    • HMasterInterface暴露的接口Table(createTable, modifyTable, removeTable, enable, disable),ColumnFamily (addColumn, modifyColumn, removeColumn),Region (move, assign, unassign)
    • Master运行的后台线程:LoadBalancer线程,控制region来平衡集群的负载。CatalogJanitor线程,周期性的检查hbase:meta表。
  • HRegionServer是RegionServer的实现,服务和管理Regions,集群中RegionServer运行在DataNode。
    • HRegionRegionInterface暴露接口Data (get, put, delete, next, etc.),Region (splitRegion, compactRegion, etc.)
    • RegionServer后台线程:CompactSplitThread,MajorCompactionChecker,MemStoreFlusher,LogRoller。
  • Regions,代表table,Region有多个Store(列簇),Store有一个Memstore和多个StoreFiles(HFiles),StoreFiles的底层是Block

HLog, 预写日志文件,也叫做WAL(write-ahead log)。

  • 通常情况,每个RegionServer只有一个WAL实例。
  • MultiWAL: 如果每个RegionServer只有一个WAL,由于HDFS必须是连续的,导致必须写WAL连续的,然后出现性能问题。MultiWAL可以让RegionServer同时写多个WAL并行的,通过HDFS底层的多管道,最终提升总的吞吐量,但是不会提升单个Region的吞吐量。
  • WAL的配置:
// 启用multiwal
<property><name>hbase.wal.provider</name><value>multiwal</value>
</property>

HFile 真实的数据存储文件。HFile的生成方式:

  • 起初,HFile中并没有任何Block,数据还存在于MemStore中。
  • Flush发生时,创建HFile Writer,第一个空的Data Block出现,初始化后的Data Block中为Header部分预留了空间,Header部分用来存放一个Data Block的元数据信息。
  • 而后,位于MemStore中的KeyValues被一个个append到位于内存中的第一个Data Block中:
    注:如果配置了Data Block Encoding,则会在Append KeyValue的时候进行同步编码,编码后的数据不再是单纯的KeyValue模式。Data Block Encoding是HBase为了降低KeyValue结构性膨胀而提供的内部编码机制。

二、Hbase的读写数据流程

HBase用-ROOT-表记录.META.表的位置信息(即元数据信息),而.META.表记录了用户表Region的位置信息。

要搞清楚hbase的读写流程,首先来看hbase的几张系统表:
hbase:namespace 存储了hbase中的所有namespace的信息

hbase:meta 存储了hbase中所有的region的信息,包括rowkey范围,region所在的regionserver的地址

hbase:meta 在zookeeper中,进入zookeeper中查看

hbase的读流程:

  • 1、Client 先访问 zookeeper,找到 Meta 表,并获取 Meta 表元数据。。
  • 2、找到meta表所在的regionserver的地址。
  • 3、访问对应的regionserver,读meta表的信息。
  • 4、通过命令找到rowkey对应的region,得到region的名称。
  • 5、访问region所在的regionserver。
  • 6、Client到HRegion的中去查找数据,首先到MemStore中查找,查到直接返回;查不到就去BlockCache中查找,查到直接返回;再查不到就去StoreFile中读数据,把读到的数据存入BlockCache中再返回Client

一个 RegionServer 上有一个 BlockCache 和N个 Memstore它们的大小之和不能大于等于 heapsize * 0.8,否则 hbase 不能启动。默认 BlockCache 为 0.2,而 Memstore 为 0.4。对于注重读响应时间的系统,应该将 BlockCache 设大些,比如设置BlockCache =0.4,Memstore=0.39。这会加大缓存命中率。

hbase的写流程:

  • 1、Client通过Zookeeper调度获取表的元数据信息。
  • 2、Cilent通过rpc协议与RegionServer交互,通过-ROOT-表与.META.表找到对应的对应的Region。
  • 3、将数据写入HLog日志中,如出现意外可以通过HLog恢复信息。
  • 4、将数据写入Region的MemStore中,当MemStore达到阈值开始溢写,将其中的数据Flush成一个StoreFile。
  • 5、MemStore不断生成新的StoreFile,当StoreFile的数量到达阈值后会出发Compact合并操作,将多个StoreFile合并成一个StoreFile。
  • 6、StoreFile文件会不断增大,当达到阈值后会出发Split操作,把当前的Region且分为两个新的Region。**父Region会下线,**两个子Region会被HMaster分配到相应的RegionServer。

数据写到store以后是先缓存在memstore中,同一个region中存在多个列族则存在多个store,每个store都一个memstore,当其实memstore进行flush时,属于同一个region
的store中的memstore都会进行flush。

HBase的流程高性能:

  • 1、由读写数据的流程可以发现,Region中的内存分为两块:MemStore(负责写数据)、BlockCache(负责读数据),这是HBase的一大特点——读写分离,这也是HBase读写速度极快的原因之一。
  • 2、在HBase中,可以看出只有增添操作,所有的更新和删除都是在后续的Compact合并过程中进行的,这使得用户的写操作只有进入内存就可以立刻返回,实现了I/O的高性能。

Hbase的storeFile合并的两种方式minor 和 major

hbase中有两种类型的合并

  • minor compaction 小合并
  • major compaction 大合并

minor compaction 小合并

  • 多个StoreFile合并成一个更大的StoreFile
    这个过程是将多个小的、相近的StoreFile合并成一个更大的StoreFile,对于超过TTL(Time To Live)的数据、更新的数据和删除的数据仅仅做个了标记(即新增了一个带有标记的版本号),并没有进行物理删除,一次minor compaction的结果会得到更少、更大的StoreFile。这种合并的触发频率很高
  • minor compaction触发的条件:
    • 表示一次minor compaction中最多选取10个store file
    • 文件大小小于该值的store file (128MB)一定会加入到minor compaction的store file中
    • 默认值为LONG.MAX_VALUE,表示文件大小大于该值的store file 会被minor compaction排除
<!--表示至少需要三个满足条件的store file时,minor compaction才会启动-->
<property><name>hbase.hstore.compactionThreshold</name><value>3</value>
</property><!--表示一次minor compaction中最多选取10个store file-->
<property><name>hbase.hstore.compaction.max</name><value>10</value>
</property><!--默认值为128m,
表示文件大小小于该值的store file 一定会加入到minor compaction的store file中
-->
<property><name>hbase.hstore.compaction.min.size</name><value>134217728</value>
</property><!--默认值为LONG.MAX_VALUE,表示文件大小大于该值的store file 会被minor compaction排除-->
<property><name>hbase.hstore.compaction.max.size</name><value>9223372036854775807</value>
</property>

major compaction 大合并

  • 将一个Store中的所有StoreFile合并成一个HFile
    这个过程会把已经删除的、TTL过期的数据,版本号超过设定版本号的数据(版本太多的老数据)。这种合并频率比较低,默认是7天执行一次,并且性能消耗很大,一般都是手动控制合并,防止自动合并出现在业务高峰期
  • major compactiom的触发条件:默认7天一次
<!--默认值为7天进行一次大合并,-->
<property><name>hbase.hregion.majorcompaction</name><value>604800000</value>
</property>
  • 手动触发:使用major_compact命令
##使用major_compact命令
major_compact tableName

三、Hbase的应用场景

  • 对象存储:我们知道不少的头条类、新闻类的的新闻、网页、图片存储在HBase之中,一些病毒公司的病毒库也是存储在HBase之中
  • 时序数据:HBase之上有OpenTSDB模块,可以满足时序类场景的需求
  • 推荐画像:特别是用户的画像,是一个比较大的稀疏矩阵,蚂蚁的风控就是构建在HBase之上
  • 时空数据:主要是轨迹、气象网格之类,滴滴打车的轨迹数据主要存在HBase之中,另外在技术所有大一点的数据量的车联网企业,数据都是存在HBase之中
  • CubeDB OLAP:Kylin一个cube分析工具,底层的数据就是存储在HBase之中,不少客户自己基于离线计算构建cube存储在hbase之中,满足在线报表查询的需求
  • 消息/订单:在电信领域、银行领域,不少的订单查询底层的存储,另外不少通信、消息同步的应用构建在HBase之上
  • Feeds流:典型的应用就是xx朋友圈类似的应用
  • NewSQL:之上有Phoenix的插件,可以满足二级索引、SQL的需求,对接传统数据需要SQL非事务的需求

四、Hbase的优化

1、zookeeper.session.timeout(默认时间是:3分钟(180000ms))

该值可视情况调大,防止假掉线引起的数据rebalance。

2、hbase.hregion.memstore.mslab.enabled

是否开启mslab方案,减少因内存碎片导致的Full GC,提高整体性能.
线上配置:true
默认配置:true

3、垃圾回收(GC)参数配置

在hbase做GC的时候,我们采用CMS方式做回收是没问题的,也是正确方式。但是这个CMS 这种标记回收默认是当老年代内存达到90%的时候,开始做回收;但是可以想象一下这样的场景:假如此时老年代内存达到了90%,老年代开始CMS的并发收集,此时年轻代还在不断的把对象晋升到老年代,那么这个时候就很可能出现,老年代的CMS还没完成标记,老年代的空间就满了,那么这个时候就会出现比较严重的full GC ,停掉所有正在运行的线程,然后以单线程的方式去做回收,这个时间是很漫长的;所以我们最好用:-XX:CMSInitiatingOccupancyFraction=N(默认90)这个参数去控制,不要把老年代的GC设置的这么高,调节到60%就可以

4、HBase内存管理

HBase上的Regionserver的内存主要分为两部分,一部分作为Memstore,主要用来写;一部分作为BlockCache,主要用于读。
写请求会先写入Memstore,Regionserver会给每个region提供一个Memstore,当Memstore满128M(hbase.hregion.memstore.flush.size)以后,会启动flush刷新到磁盘,当Memstore的总大小超过限制时(heapsizehbase.regionserver.global.memstore.upperLimit0.9),会强行启动flush进程,从最大的Memstore开始flush知道低于限制

读请求先到Memstore中查数据,查不到就到BlockCache中查,再查不到就会到磁盘上读,并把读的结果放入BlockCache。由于ClockCache采用的是LRU(最近最少使用)策略,因此BlockCache达到上限(heapsizehfile.block.cache.size0.85)后,会启动淘汰机制,淘汰掉最老的一批数据。
在注重读响应时间的应用场景下,可以将BlockCache设置大些,Memstore设置小些,以加大缓存命中率

5、启动SNAPPY压缩

HBase列存储,比较占用空间,所以一般需要采用压缩算法,(从mysql导入hbase数据时发现,原本在mysql中30G数据,在hbase中占用150G),其中snappy性能优异,而且CDH中,直接安装了snappy的库。

使用方式:1、创建时指定格式;hbase> create 'test', { NAME => 'c', COMPRESSION => 'SNAPPY' }2、修改已经创建好的列簇的压缩格式disable 'test'alter 'test', NAME => 'c', COMPRESSION => 'snappy'enable 'test'major_compact 'test'   --修改之后,需要做一个major合并才能养压缩格式生效describe 'test'  --查看有没有生效
6、预创建Region

创建HBase时,就预先根据可能的RowKey划分出多个Region而不是默认的一个,从而可以将后续的读写操作负载均衡到不同的Region上,避免热点现象;
HBase表的预分区需哟啊紧密结合业务场景来选择分区的key值,每个region都有一个startKey和一个endKey来表示该region存储的rowKey范围;

7、避免Region热点

热点现象:某个小的时段内,对HBase的读写请求集中到极少数的Region上,导致这些Region所在的RegionServer处理请求量骤增,负载量明显偏大,而其他的RegionServer明显空闲;
出现的原因:主要是因为Hbase表设计时,rowKey设计不合理造成的;
解决办法:Rowkey的随机散列+创表预分区
RowKey设计原则
1、总的原则:避免热点现象,提高读写性能;
2、长度原则:最大长度64KB,开发通常10-16个字节,因为Hbase中每个单元格是以key-value进行存储的,因此每个value都会存储rowkey,所以rowkey越来越占空间;
3、散列原则:将时间上连续产生的rowkey散列化,以避免集中到极少数Region上
4、唯一原则:必须在设计上保证rowkey的唯一性
RowKey设计结合业务:
在满足rowkey设计原则的基础上,往往需要将经常用于查询的字段整合到rowkey上,以提高检索查询效率

8、手动进行major compact

实际应用中,可以考虑必要时手动进行major compact,将同一个row key的修改进行合并形成一个大的StoreFile。同时,可以将StoreFile设置大些,减少split的发生。
合并小的storeFile成大的storeFile。在hbase中,主要存在两种类型的compaction:minor compaction和major compaction。

设置major compaction禁止自动执行,将值设为0:

<property><name>hbase.hregion.majorcompaction</name><value>0</value>
</property>

五、Hbase为什么写快读慢

HBase采用LSM树存储结构
LSM树本质是在读写之间取得平衡,它首先在内存中构建一颗有序的小树,随着小树的逐渐增大,达到一定阈值时会flush到磁盘上。所以LSM树不像B+树一样是一棵完整的大树,一棵LSM树就是一个个B+树合起来
多次flush之后会形成多个数据存储文件,后台线程会按照配置自动将多个文件合并成一个,此时多颗小树就会被合并成一棵大树。
但是读取时,由于不知道数据在哪棵小树上,因此必须遍历所有小树(所以才说LSM牺牲了部分读的性能),每棵小树内部数据是有序的。查询是先查内存中的部分,再去查磁盘上的部分。

这也就解释了为什么要有WAL了:
因为数据是先存在内存中的,不会立即写到磁盘上,断点数据就丢失了,所以为了保护内存中的数据需要写在磁盘上记录LogFile。当内存中的数据flush到磁盘上时,就可以删除掉相应的LogFile了。

这也就解释了为什么需要compact了:
因为上面说了,读的时候是要遍历所有小树的,小树越多,读的性能就会越来越差,所以需要进行merge,将多颗小树变成一颗大树

LSM树和B+树相比,LSM树放弃了部分读性能,使用顺序写来大幅提高写性能,适合写多读少以及大规模数据读取;而B+树更加适合读多写少的场景
HBase本身设计(应当说是底层Hadoop的设计)就是更加偏向于写多读少的场景,所以使用LSM更加合适。

六、Hbase是cp还是ap架构

结论:hbase是CAP中的CP系统,即hbase是强一致性的。

  • hbase之所以是CP系统,实际和底层HDFS无关不大,它是CP系统,是因为对每一个region同时只有一台RegionServer为它服务,对一个region所有的操作请求,都由这一台region server来响应,自然是强一致性的。
  • 在这台RegionServer fail的时候,它管理的region会failover到其他Region Server时,需要根据WAL log来redo,这时候进行redo的region应该是unavailable(不可用)的,所以hbase降低了可用性,提高了一致性。
  • 设想一下,如果redo的region能够响应请求,那么可用性提高了,则必然会返回不一致的数据(因为redo可能还没完成),从这个角度来看hbase就是降低一致性来提高了可用性。

CAP 结构中的 cp(强一致性) 和 ap(高可用性)。

HBase上面regionserver宕机之后的处理
1.zookeeper上面没收到regionserver心跳,发现掉线
2.HLog进行拆分,分配到相应的region上面
3.region分发到相应的活着的regionserver上面
4.根据分给的region上面的HLog,持久化到新的HFile

七、Hbase 的scan

首先,对于scan来说,并不是所有的都会扫描全表。

scan的几种实现

scan是较为底层的也是用的最多的一种获取Hbase中数据的方式,在它的上面还封装了几种基于scan的获取方式的数据,例如snapshotScanMR,TableScanMR,scanMR。这几中方式都是基于scan,用MR的方式去获取数据,并且对于获取大批量的数据来说,效率都比scan好的多。

非全表scan的两种方式

  • 借助Rowkey:scan可以根据rowkey,cf,column,timestamp,filter来获取方式。在这里优先推荐根据rowkey的方式获取数据,即可以指定startrow和endrow,也可以指定具体的某个行键去获取数据。在源码中也指出了如果具体指定了rowkey,那么会只是扫描那一段的数据。众所周知,hbase底层存储数据是根据rowkey的字典顺序存储数据的,所以如果使用rowkey的方式去查找,scan就可以顺序查找,大大缩短了时间。
  • 第二种就是根据timestamp去查找,对于这个时间戳,特别注意的是指的是存入hbase中的时间在存入时,对应的cell中会记录下来。而不是客户端插入的数据的时间,这里肯定会有一定的使时间偏移,但相差不会很大。对于timestamp的方式来说,它也是只是去扫描对应范围或者对应某个时间戳去获取。

其他的方式,就是通过全表扫描去查询的。

在用scan查询的时候,底层有个next()方法,一次默认返回100条数据(或者不超过2m的数据),这不同于scan中的setBatch()方法,这里返回的是给hbase服务器的值而不是返回给客户端的值,怎么做是为了避免在全表扫描的时候
一次返回太多数据,导致OOM。

八、Hbase 的rowkey设计

访问hbase table中的行,只有三种方式:

  • 1 通过单个row key访问
  • 2 通过row key的range
  • 3 全表扫描

hbase rowkey如何设计才能散列到不同的节点上?

即时间上连续的数据。这些数据可能来自于某个传感器网络、证券交易或者一个监控系统。它们显著的特点就是rowkey中含有事件发生时间。带来的一个问题便是HBase对于row的不均衡分布,它们被存储在一个唯一的rowkey区间中,被称为region,区间的范围被称为Start Key和End Key。

对于单调递增的时间类型数据,很容易被散列到同一个Region中,这样它们会被存储在同一个服务器上,从而所有的访问和更新操作都会集中到这一台服务器上,从而在集群中形成一个hot spot,从而不能将集群的整体性能发挥出来。

要解决这个问题是非常容易的,只需要将所有的数据散列到全部的Region上即可。这是可以做到的,比如,在rowkey前面加上一个非线程序列,常常有如下选择:

Hash散列

可以使用一个Hash前缀来保证所有的行被分发到多个Region服务器上。例如:

byte prefix =
(byte) (Long.hashCode(timestamp) % <number of regionservers>);
byte[] rowkey =
Bytes.add(Bytes.toBytes(prefix), Bytes.toBytes(timestamp);

这个公式可以产生足够的数字,将数据散列到所有的Region服务器上。当然,公式里假定了Region服务器的数目。如果您打算后期扩容您的集群,那么您可以把它先设置为集群的整数倍。生成的rowkey类似下面:

0myrowkey-1,
1myrowkey-2, 2myrowkey-3, 0myrowkey-4, 1myrowkey-5, \
2myrowkey-6, …

当他们将按如下顺序被发送到各个Region服务器上去:

0myrowkey-1
0myrowkey-4
1myrowkey-2
1myrowkey-5
…

换句话说,对于0myrowkey-1和0myrowkey-4的更新操作会被发送到同一个region服务器上去(假定它们没有被散列到两个region上去),1myrowkey-2和1myrowkey-5会被发送到同一台服务器上。

这种方式的缺点是rowkey的范围必须通过代码来控制,同时对数据的访问,可能要访问多台region服务器。当然,可以通过多个线程同时访问,来实现并行化的数据读取。这种类似于只有map的MapReduce任务,可以大大增加IO的性能。

翻转字段

比如将时间戳翻转,来防止rowkey热点问题。

查找时:可以通过scan.setStartRow 和 scan.setStopRow 来设置查找的范围,startrow 和 endrow 也要做相应的翻转。

import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.hbase.HBaseConfiguration;
import org.apache.hadoop.hbase.client.*;
import org.apache.hadoop.hbase.filter.*;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
/*todo  查hbase数据条数*/
public class HBaseLocalTest {public static Configuration conf;public static Connection conn;static {conf = HBaseConfiguration.create();conf.set("hbase.zookeeper.property.clientPort", "2181");conf.set("hbase.zookeeper.quorum", "*");try {conn = ConnectionFactory.createConnection(conf);} catch (IOException e) {e.printStackTrace();}}//将传入的日期参数转换成rowkey的反转public static String Fdate(String s) {char[] array = s.toCharArray();String reverse = "";//倒叙拿出for (int i = array.length - 1; i >= 0; i--)reverse += array[i];return reverse;}//补齐传入的字符串public static String Complement(String busNo) {//预先定义一个6位0StringBuilder zero =new StringBuilder("000000");String result = zero.substring(0, zero.length() - busNo.length()) + busNo;return result;}/*** 根据startRowKey和endRowKey筛选出区间,然后根据regxKey正则匹配和num查出最终的结果* @param tableName 表名* @param startRowKey 开始的范围* @param endRowKey 结束的范围* @param regxKey 正则匹配* @param num 查询的条数* @return List<Result>*/public static List<Result> getNumRegexRow(String tableName,String startRowKey,String endRowKey, String regxKey,int num) {HTableInterface table = null;List<Result> list = null;try {table = new HTable(conf, tableName);//创建一个过滤器容器,并设置其关系(AND/OR)FilterList fl = new FilterList(FilterList.Operator.MUST_PASS_ALL);//设置正则过滤器RegexStringComparator rc = new RegexStringComparator(regxKey);RowFilter rf = new RowFilter(CompareFilter.CompareOp.EQUAL, rc);//过滤获取的条数 if (num != 0) {Filter filterNum = new PageFilter(num);//展示条数fl.addFilter(filterNum);}//过滤器的添加fl.addFilter(rf);Scan scan = new Scan();//设置取值范围scan.setStartRow(startRowKey.getBytes());//开始的keyscan.setStopRow(endRowKey.getBytes());//结束的keyscan.setFilter(fl);//为查询设置过滤器的listResultScanner scanner = table.getScanner(scan) ;list = new ArrayList<Result>() ;for (Result rs : scanner) {list.add(rs) ;}} catch (Exception e) {e.printStackTrace() ;}finally{try {table.close() ;} catch (IOException e) {e.printStackTrace();}}return list;}public static void main(String[] args) throws Exception {String startDate= "181017";String endDate ="181017";String tablename = "Table";String zao="00";  //这里是根据一天24小时匹配查询String wan="23";String wei = "000000001";String wei2= "999999999";String startRowkey = Fdate(startDate)+zao+wei;String endRowkey = Fdate(endDate)+wan+wei2;List<Result> list = getNumRegexRow(tablename,startRowkey,endRowkey,"[^\\\\\\/\\^]",0);  //后面的0,是查询所有符合的。如果改为5,只会打印符合条件的前5条数据for (int j = 0; j < list.size(); j++) {//            System.out.print("PROID:");  //下面是打印字段的值
//            System.out.print(Bytes.toString(list.get(j).getValue(Bytes.toBytes("YB"),Bytes.toBytes("PROID"))));
//            System.out.print("     ORIDATA:");
//            System.out.println(Bytes.toString(list.get(j).getValue(Bytes.toBytes("YB"),Bytes.toBytes("ORIDATA"))));
            System.out.print("     SITE_TIME:");
            System.out.print(Bytes.toString(list.get(j).getValue(Bytes.toBytes("f"),Bytes.toBytes("SITE_TIME"))));
            System.out.print("     DOWN:");
            System.out.print(Bytes.toString(list.get(j).getValue(Bytes.toBytes("f"),Bytes.toBytes("IS_UP+DOWN"))));
            System.out.print("     LAT:");
            System.out.print(Bytes.toString(list.get(j).getValue(Bytes.toBytes("f"),Bytes.toBytes("LAT"))));
            System.out.print("     LNG:");
            System.out.println(Bytes.toString(list.get(j).getValue(Bytes.toBytes("f"),Bytes.toBytes("LNG"))));}System.out.println("数据量:"+list.size());conn.close();}
}

九、请详细描述 Hbase 中一个 Cell 的结构

HBase 中通过 row 和 columns 确定的为一个存贮单元称为 cell。Cell:由{row key, column(= + ), version}是唯一确定的单元cell 中的数据是没有类型的,全部是字节码形式存贮。

十、简述 Hbase filter 的实现原理是什么?结合实际项目经验,写出几个使用filter 的场景。

HBase 为筛选数据提供了一组过滤器,通过这个过滤器可以在 HBase 中的数据的多个维度(行,列,数据版本)上进行对数据的筛选操作,也就是说过滤器最终能够筛选的数据能够细化到具体的一个存储单元格上(由行键, 列名,时间戳定位)。

RowFilter、PrefixFilter。hbase 的 filter 是通过 scan 设置的,所以是基于 scan 的查询结果进行过滤. 过滤器的类型很多,但是可以分为两大类——比较过滤器,专用过滤器。过滤器的作用是在服务端判断数据是否满足条件,然后只将满足条件的数据返回给客户端;如在进行订单开发的时候,我们使用 rowkeyfilter 过滤出某个用户的所有订单。

相关的过滤方法使用:

  • 提取rowkey以01结尾数据
    Filter filter = new RowFilter(CompareFilter.CompareOp.EQUAL,new RegexStringComparator(".*01$"));
  • 提取rowkey以包含201407的数据
    Filter filter = new RowFilter(CompareFilter.CompareOp.EQUAL,new SubstringComparator(“201407”));
  • 提取rowkey以123开头的数据
    Filter filter = new RowFilter(CompareFilter.CompareOp.EQUAL,new BinaryPrefixComparator(“123”.getBytes()));

十一、hbase 的存储结构?

Hbase 中的每张表都通过行键 (rowkey) 按照一定的范围被分割成多个子表(HRegion),默认一个 HRegion 超过 256M 就要被分割成两个,由 HRegionServer 管理,管理哪些 HRegion 由 Hmaster 分配。 HRegion 存取一个子表时,会创建一个 HRegion 对象然后对表的每个列族 (Column Family) 创建一个 store 实例, 每个 store 都会有 0个或多个 StoreFile 与之对应,每个 StoreFile 都会对应一个 HFile , HFile 就是实际的存储文件
HFile 是HBase 使用的底层存储格式。**HFile 对应于列族,一个列族可以有多个 HFile,但一个 HFile 不能存储多个列族的数据。**在集群的每个节点上,每个列族有一个MemStore

十二、HBase 宕机如何处理?

宕机分为 HMaster 宕机和 HRegisoner 宕机.

  • 如果是 HRegisoner 宕机,HMaster 会将其所管理的 region 重新分布到其他活动的 RegionServer 上,由于数据和日志都持久在 HDFS 中,该操作不会导致数据丢失,所以数据的一致性和安全性是有保障的。
  • 如果是 HMaster 宕机, HMaster 没有单点问题, HBase 中可以启动多个HMaster,通过 Zookeeper 的 Master Election 机制保证总有一个 Master 运行。即ZooKeeper 会保证总会有一个 HMaster 在对外提供服务。

十三、Hmaster高可用部署

  • 2.1 创建backup-masters文件
    在wyl01机器上hbase的conf目录下创建backup-masters文件,文件内容如下:
cd /opt/hbase/conf
vim  backup-masters
# 添加以下内容,# wyl01是之前的master节点,现在是让wyl02成为别用的master节点
wyl02
  • 2.2 分发到其他的两台机器
scp -r backup-masters wyl02:/opt/hbase/conf/scp -r backup-masters wyl03:/opt/hbase/conf/
  • 2.3 启动服务
#在wyl01机器上执行启动脚本
cd /opt/hbase/bin
./start-hbase.sh

十四、hbase之布隆过滤器

布隆过滤器(Bloom Filter)是1970由布隆提出的。通过一个很长的二进制向量与一系列随机哈希函数生成。
布隆过滤器是hbase中的高级功能,它能够减少特定访问模式(get/scan)下的查询时间。不过由于这种模式增加了内存和存储的负担,所以被默认为关闭状态。

hbase支持如下类型的布隆过滤器:

  • 1、NONE 不使用布隆过滤器
  • 2、ROW 行键使用布隆过滤器
  • 3、ROWCOL 列键使用布隆过滤器

其中ROWCOL是粒度更细的模式。

当我们随机读get数据时,如果采用hbase的块索引机制,hbase会加载很多块文件。如果采用布隆过滤器后,它能够准确判断该HFile的所有数据块中,是否含有我们查询的数据,从而大大减少不必要的块加载,从而增加hbase集群的吞吐率。

1、布隆过滤器的存储在哪
对于hbase而言,当我们选择采用布隆过滤器之后,HBase会在生成StoreFile(HFile)时包含一份布隆过滤器结构的数据,称其为MetaBlock;MetaBlock与DataBlock(真实的KeyValue数据)一起由LRUBlockCache维护。所以,开启bloomfilter会有一定的存储及内存cache开销。但是在大多数情况下,这些负担相对于布隆过滤器带来的好处是可以接受的。

2、采用布隆过滤器后,hbase如何get数据
在读取数据时,hbase会首先在布隆过滤器中查询,根据布隆过滤器的结果,再在MemStore中查询,blockcache中查找,最后再在对应的HFile中查询

3、采用ROW还是ROWCOL布隆过滤器
这取决于用户的使用模式。如果用户只做行扫描,使用更加细粒度的行加列布隆过滤器不会有任何的帮助,这种场景就应该使用行级布隆过滤器。当用户不能批量更新特定的一行,并且最后的使用存储文件都含有改行的一部分时,行加列级的布隆过滤器更加有用。

理论知识:
https://zhuanlan.zhihu.com/p/93853964
https://blog.csdn.net/qq_32445015/article/details/101926881

参考资料:
https://www.cnblogs.com/kaiwen03/p/9847877.html

HBASE原理及使用相关推荐

  1. hbase原理与实践_HBase 性能调优第一弹:内存篇

    这是使用 HBase 最不可避免的一个话题,就是 HBase 的性能调优,而且通常建立在我们对 HBase 内部运行机制比较了解的基础上进行的,因此无论怎么说,调优这块都是一个相对复杂的事情.这一篇我 ...

  2. HBase原理 – snapshot 快照

    目录 snapshot(快照)基础原理 snapshot能实现什么功能? hbase snapshot用法大全 hbase snapshot分布式架构-两阶段提交 snapshot核心实现 clone ...

  3. HBase原理之数据读取流程

    和写流程相比,HBase读数据是一个更加复杂的操作流程,这主要基于两个方面的原因:其一是因为整个HBase存储引擎基于LSM-Like树实现,因此一次范围查询可能会涉及多个分片.多块缓存甚至多个数据存 ...

  4. HBase学习(7)-HBase原理

    原文来自:扎心了,老铁的<HBase学习之路 (七)HBase 原理>

  5. 《HBase原理与实践》阅读笔记

    学习笔记(1-3章) 全书概述 1.HBase概述 1.1.Hbase发展历史 1.2.Hbase数据模型 1.3.Hbase体系结构 1.4.Hbase系统特性 2.Hbase基础数据结构与算法 2 ...

  6. Hbase原理与使用

    hbase hbase简介 1.1. 什么是hbase HBASE是一个高可靠性.高性能.面向列.可伸缩的分布式存储系统,利用HBASE技术可在廉价PC Server上搭建起大规模结构化存储集群. H ...

  7. HBase原理深入解析(一)----HBase架构总览

    前言:掌握Hbase的重要性不言而喻,掌握Hbase的设计原理更是重中之重.本文是对HBase原理进行讲解系列文章的开篇,尽量详细地从整体上介绍HBase的架构,对每个部分的名词进行初步解释,使我们对 ...

  8. Hbase原理与实践(学习笔记一:基本概念):

    相关笔记: <Hbase原理与实践>读书笔记--1.HBase概述_凯哥多帅哦的博客-CSDN博客_hbase的实现原理1.1 HBase前世今生Google当年风靡一时的"三篇 ...

  9. HBase原理详细概述

    HBase,Hadoop DataBase的简称 是一种非关系型数据库,not only SQL. HBase是一个分布式的架构,底层是HDFS的架构,由各个DataNode组成. HBase体系结构 ...

  10. HBase原理解析(转)

    本文属于转载,原文链接:http://www.aboutyun.com/thread-7199-1-1.html 前提是大家至少了解HBase的基本需求和组件. 从大家最熟悉的客户端发起请求开始讲起吧 ...

最新文章

  1. launchctl mysql_Mac Yosemite 10.10 下利用 Launchctl 自启动 mysql
  2. 第8期Datawhale组队学习计划
  3. JS数组方法(forEach()、every()、reduce())
  4. 完美主义怎么解决_相信我,你不要完美主义
  5. mysql存储过程并行_Mysql存储过程的执行顺序问题
  6. jqprint获取打印页数_高年级应用题40道,假期快给孩子打印练习吧!(含答案)...
  7. uvc能支持多大分辨率_华为手环B5测评:该有的功能一个不缺,甚至还能变身蓝牙耳机...
  8. 利用openpyxl模块来操作Excel
  9. php 遍历目录下的子目录文件,PHP获取目录及子目录下指定后缀的所有文件
  10. 四大网络抓包神器,总有一款适合你~
  11. 冲刺周期一--站立会议05
  12. PSFTP工具的使用教程
  13. html设置ie11兼容,ie11浏览器兼容性问题设置方法
  14. 向Spring大佬低头——大量源码流出解析
  15. java base64 加号_Base64 空格,加号问题
  16. 2021 CCPC 哈尔滨 E. Power and Modulo (思维题)
  17. 简单分类模型设计与实现
  18. (50)uniGUI 高大上的HyperServer-多机部署一个硬集群
  19. 学习人工智能需要哪些必备基础
  20. mta计算机证书有用么,微软MTA认证有用吗 微软MTA证书含金量高吗

热门文章

  1. 【弗洛伊得算法的改良(可以求出具体的路径)】
  2. 第三方支付平台是什么意思?
  3. 外滩十八号的长笛女孩[转]
  4. 上市公司9月28日晚间公告速递
  5. springboot自带定时器实现定时任务的开启关闭以及定时时间可以配置
  6. 安卓app内存测试脚本(分场景测试)
  7. 小程序微信支付接口php,微信小程序微信支付接入开发
  8. 德国区块链游说倡导组织:德国政府欢迎区块链,正制定ICO监管政策
  9. 窥探晶体世界的奥秘 —— 230种空间群晶体结构模型全在这里
  10. 任意长度的python列表_在Python中压扁任意嵌套列表的最快方法是什么?