单点模式
1 选择Hbase版本要与hadoop版本相对应.
下载地址:http://mirrors.cnnic.cn/apache/hbase
2 安装,解压下载的tar文件
3 配置conf/hbase-site.xml 去配置hbase.rootdir,来选择Hbase将数据写到哪个目录
单机配置,只需要如下配置hbase-site.xml:
<property>
<name>hbase.rootdir</name>
<value> file:///home/grid/hbase/data </value>
<description>The directory sharedbyRegionServers. </description>
</property>
单击配置:<value>file:///home/grid/hbase/data</value>
4 修改hbase-env.sh :需要修改 JAVA_HOME
5 启动HBase
$ ./bin/start-hbase.sh
6 运行java :jps命令 出现进程HMaster
7 bin/hbase shell 命令 出现版本号 quit 退出 单机版安装成功
伪分布模式
单点模式基础上
编辑hbase-env.sh 增加HBASE_CLASSPATH环境变量,值为hadoop配置文件的目录
HBASE_CLASSPATH=/web/hadoop/conf
编辑hbase-site.xml打开分布模式
<configuration>
<property>
<name>hbase.rootdir</name>
<value>hdfs://master:9000/hbase</value>
<description>The directory sharedbyRegionServers.habase数据存储位置改为hadoop中 </description>
</property>
//设置zookeeper的主机, localhost在host中的解析一定要有
<property>
<name>hbase.zookeeper.quorum</name>
<value>localhost</value>
</property>
//开启分布式模式
<property>
<name>hbase.cluster.distributed</name>
<value>true</value>
</property>
</configuration>
覆盖hadoop核心jar包(不同版本不一样)
启动hbase
./start-hbase.sh
验证启动
1) 运行jps命令看进程 多了下面三个进程 HRegionServer、HQuorumPeer、HMaster
2) http://192.168.102.136:60010/master.jsp,查看hbase运行情况
HBASE 中shell使用
输入错误用ctrl+del 或 ctrl+backspace 可以删除
进入shell命令界面: Hbase shell
整个学是在网上搜到的,照着整个的操作一遍,作为学习记录:
来自:http://www.cnblogs.com/linjiqin/archive/2013/03/08/2949339.html
学生成绩表作为例子:
一、 列与列簇理解:
这里 grad 对于表来说是一个列,course 对于表来说是一个列族,这个列族由三个列组成 china、math 和 english,当然我们可以根据我们的需要在 course 中建立更多的列族,如computer,physics 等相应的列添加入 course 列族。(备注:列族下面的列也是可以没有名字的。
二、 Hbase中没有数据类型,所有数据都是字符类型。
三、 时间戳系统会自动创建,也可强行插入
四、 官网API:http://hbase.apache.org/apidocs/index.html
五、 命令使用
1) Create命令
创建一个具有两个列簇“grad”和“course”的表“scores”。其中表名、行和列都要用单引号括起来并用逗号隔开,
create 'scores', 'name', 'grad', 'course'
2) list命令
查看当前HBase中具有那些表,> list
3) Describe 命令
查看表“scores”的构造 >describe ‘scores’
4) Put命令
使用 put 命令向表中插入数据,参数分别为表名、行名(行健唯一)、列名和值,其中列名前需要列族最为前缀,时间戳由系统自动生成。
格式: put 表名,行名,列名([列族:列名]),值
例子:hbase(main):012:0> put 'scores', 'xiapi', 'grad:', '1'
hbase(main):012:0> put 'scores', 'xiapi', 'grad:', '2' --修改操作(update)
b. 给“xiapi”这一行的数据的列族“course”添加一列“<china,97>”。
hbase(main):012:0> put 'scores', 'xiapi', 'course:china', '97'
hbase(main):012:0> put 'scores', 'xiapi', 'course:math', '128'
hbase(main):012:0> put 'scores', 'xiapi', 'course:english', '85'
5) get 命令
a.查看表“scores”中的行“xiapi”的相关数据。
hbase(main):012:0> get 'scores', 'xiapi'
b.查看表“scores”中行“xiapi”列“course :math”的值。
hbase(main):012:0> get 'scores', 'xiapi', 'course :math'
或者
hbase(main):012:0> get 'scores', 'xiapi', {COLUMN=>'course:math'}
hbase(main):012:0> get 'scores', 'xiapi', {COLUMNS=>'course:math'}
备注:COLUMN 和 COLUMNS 是不同的,scan 操作中的 COLUMNS 指定的是表的列族, get操作中的 COLUMN 指定的是特定的列,COLUMNS 的值实质上为“列族:列修饰符”。
6) scan 命令
a. 查看表“scores”中的所有数据。
hbase(main):012:0> scan 'scores'
注意:
scan 命令可以指定 startrow,stoprow 来 scan 多个 row。
例如:
scan 'user_test',{COLUMNS =>'info:username',LIMIT =>10, STARTROW => 'test', STOPROW=>'test2'}
b.查看表“scores”中列族“course”的所有数据。
hbase(main):012:0> scan 'scores', {COLUMN => 'grad'}
hbase(main):012:0> scan 'scores', {COLUMN=>'course:math'}
hbase(main):012:0> scan 'scores', {COLUMNS => 'course'}
hbase(main):012:0> scan 'scores', {COLUMNS => 'course'}
7) count 命令
hbase(main):068:0> count 'scores'
8) exists 命令
hbase(main):071:0> exists 'scores'
9) delete 命令
删除表“scores”中行为“xiaoxue”, 列族“course”中的“math”。
hbase(main):012:0> delete 'scores', 'xiapi', 'course:math'
10) truncate 命令
hbase(main):012:0> truncate 'scores'
11) disbale、drop 命令
通过“disable”和“drop”命令删除“scores”表。
hbase(main):012:0> disable 'scores' --enable 'scores'
hbase(main):012:0> drop 'scores'
12) status命令
hbase(main):072:0> status
13) version命令
hbase(main):073:0> version
六、 什么情况下使用Hbase
1) 数据查询模式已经确定,且不易改变,就是说hbase使用在某种种特定的情况下,且不能变动。
2) 告诉插入,大量读取。因为分布式系统对大量数据的存取更具优势。
3) 尽量少的有数据修改。因为hbase中的数据修改知识在后面添加一行新数据,表示覆盖前一条,大量修改浪费大量空间。(hbase基于hdfs存储不支持修改)
注意:
a) 没有辅助索引,可以通过新建另一张表作为辅助索引,查找索引,然后查询需要的数据
b) “复合行健”实现多条件查询
七、 hbase的优势:
有时间戳,适合告诉时间查询;
基于行健的查询异常快(行健可参考后面hbase的表结构),特别是最近的数据可能还在memstore里,没有io开销;
分布式处理,可以方便的添加节点。
九、hbase优化,插入和查询优化
1)快速录入数据,预分区(多个分区才可以进行并行处理)
录入数据的时候hbase默认只有一个分区,当这个分区达到一定程度的时候会split成另一个分区,这个split会比较慢,所以提前创建分区,如果数据录入的时候会根据rowkey进行比对
录入到相应的分区中。
2 )如果用默认的分区策略,则rowkey的开头要散列,这样数据才能落入到不同的分区。
或者用自定义的预分区,则数据会按照规则落入到自己定义的分区中,防止数据在同一个分区一直操作。
3)批量提交数据,数据到达一定大小才提交
//将数据自动提交功能关闭
table.setAutoFlushTo(false);
//设置数据缓存区域
table.setWriteBufferSize(64 * 1024 * 1024);
put.setWriteToWAL(false); //导数据的时候为了加快速度可以,取消写日志
//刷新缓存区
table.flushCommits();
table.close();
4)数据查询或者添加的时候要创建表的连接池HTable连接池
5)查询不要用scan,可以用ES+Hbase替代scan
6)查看表某个表的所有分区的文件:
hadoop fs -ls -R /apps/hbase/data/data//default/qixiang1
检查hbase某个region的大小,单位字节: hadoop fs -du /hbase/your_table
十、我测试的rowkey生成策略,解决预分区的问题:
1)我的数据中有个站点,且每天每个小时一个站点一条数据则rowkey为 站点号+2位的小时数字
2)不同的年月日的数据在1中的rowkey中后面添加年月日,则rowkey肯定唯一
3)计算预分区的时候用一天的数据的所有rowkey比对进行预分区,则不同年月日的数据一样也会平均的落入这个预分区中,就解决了预分区的问题。
十一、随机rowkey生成策略代码
package com.jusfoun.spark.util;
import java.io.Serializable;
import java.util.LinkedHashSet;
import org.apache.hadoop.hbase.util.Bytes;
import org.apache.hadoop.hbase.util.MD5Hash;
//import com.kktest.hbase.BitUtils;
/**
*
*
**/
public class HashRowKeyGenerator implements RowKeyGenerator , Serializable {
private static long currentId = 1;
private static long currentTime = System.currentTimeMillis();
public static void main(String[] args) {
HashRowKeyGenerator d = new HashRowKeyGenerator() ;
for(int i=0;i<10;i++){
System.out.println( d.nextId() );
}
// byte[] bs = toBytes(1482982753743l ) ;
// long l = toLong(bs, 0, bs.length);
// System.out.println( l );
}
// //每次得到的结果左移动8位,然后后面的字节依次拼接到后面
// public static long toLong(byte[] bytes, int offset, final int length) {
// long l = 0;
// for(int i = offset; i < offset + length; i++) {
// //每次计算的结果 向左移动8位,向左移动8位后低8位全为0
// l <<= 8;
// System.out.println( Long.toBinaryString( l ) );
// //上面计算的结果& 0xFF后得到高于8位全为0的结果
// long byteValue = bytes[i] & 0xFF ;
// System.out.println( Long.toBinaryString( byteValue ) );
// //当前字节结算后的结果,用异或拼接的l的低8位上面,因为l当前值的低8位全都是0,则异或后l低8位就变成了byteValue的值
// //异或运算符,相应位的值相同的,结果为 0,不相同的结果为 1。
// l ^= byteValue;
// System.out.println( Long.toBinaryString( l ) );
// System.out.println( );
// }
// return l;
// }
// //每次截取8位,然后左移8,
// public static byte[] toBytes(long val) {
//// System.out.println( "原来的长整形数据:"+val );
// byte [] b = new byte[8];
// for (int i = 7; i > 0; i--) {
// //强制转型,后留下长整形的低8位
// b[i] = (byte) val;
// String str = Long.toBinaryString( val) ;
// String lb = Long.toBinaryString( b[i] ) ;
// String lb2 = Long.toBinaryString( b[i]&0xff ) ;
//
//
// System.out.println("转换为字节:"+ str );
// System.out.println( lb );
// System.out.println( lb2 );
// //向右移动8位,则第二次循环则计算第二个8位数
// val >>>= 8;
// }
// b[0] = (byte) val;
// return b;
// }
/**
* 每次生成一个rowkey
* 并发的情况下可能存在重复
* @return
*/
public byte[] nextId()
{
try {
// System.out.println( Long.MAX_VALUE - currentTime );
currentTime = getRowKeyResult(Long.MAX_VALUE - currentTime);
byte[] currentTimeBytes = Bytes.toBytes(currentTime);
byte[] lowT = Bytes.copy(currentTimeBytes, 4, 4);
byte[] currentIdBytes = Bytes.toBytes(currentId);
byte[] lowU = Bytes.copy(currentIdBytes, 4, 4);
byte[] result = Bytes.add(MD5Hash.getMD5AsHex(Bytes.add(lowT, lowU))
.substring(0, 8).getBytes(), Bytes.toBytes(currentId));
return Bytes.toBytes( Bytes.toLong( result)+"") ;//返回 字符串的字节数组
} finally {
currentId++;
}
}
//测试方法
public byte[] nextIdTest()
{
try {
System.out.println("当前的rowkey == "+currentId);
return Bytes.toBytes(currentId+"");
} finally {
currentId++;
}
}
//得到一个字符串类型的rowkey
public String nextIdString()
{
try {
// System.out.println( Long.MAX_VALUE - currentTime );
currentTime = getRowKeyResult(Long.MAX_VALUE - currentTime);
byte[] currentTimeBytes = Bytes.toBytes(currentTime);
byte[] lowT = Bytes.copy(currentTimeBytes, 4, 4);
byte[] currentIdBytes = Bytes.toBytes(currentId);
byte[] lowU = Bytes.copy(currentIdBytes, 4, 4);
byte[] result = Bytes.add(MD5Hash.getMD5AsHex(Bytes.add(lowT, lowU))
.substring(0, 8).getBytes(), Bytes.toBytes(currentId));
return Bytes.toLong( result)+"";
} finally {
currentId++;
}
}
/**
* getRowKeyResult
* @param tmpData
* @return
*/
public static long getRowKeyResult(long tmpData)
{
String str = String.valueOf(tmpData);
StringBuffer sb = new StringBuffer();
char[] charStr = str.toCharArray();
for (int i = charStr.length -1 ; i > 0; i--)
{
sb.append(charStr[i]);
}
return Long.parseLong(sb.toString());
}
}
2)随机数预分区数组代码
package com.jusfoun.spark.util;
import java.nio.charset.Charset;
import java.util.Iterator;
import java.util.TreeSet;
import org.apache.hadoop.hbase.util.Bytes;
/**
*
* @author kuang hj
*
*/
public class HashChoreWoker{
// 随机取机数目
private int baseRecord;
// rowkey生成器
private RowKeyGenerator rkGen;
// 取样时,由取样数目及region数相除所得的数量.
private int splitKeysBase;
// splitkeys个数
private int splitKeysNumber;
// 由抽样计算出来的splitkeys结果
private byte[][] splitKeys;
/**
*
* @param baseRecord 多少条数据
* @param prepareRegions 准备多少个分区
*/
public HashChoreWoker(int baseRecord, int prepareRegions) {
this.baseRecord = baseRecord;
// 实例化rowkey生成器
rkGen = new HashRowKeyGenerator();
splitKeysNumber = prepareRegions - 1;
splitKeysBase = baseRecord / prepareRegions;
}
/**
* 根据rowkey生成规则计算一定数量的数据的 分区的 值
* @return
*/
public byte[][] calcSplitKeys() {
splitKeys = new byte[splitKeysNumber][];
// 使用treeset保存抽样数据,已排序过
TreeSet<byte[]> rows = new TreeSet<byte[]>(Bytes.BYTES_COMPARATOR);
for (int i = 0; i < baseRecord; i++) {
byte[] rowId = rkGen.nextId();
// System.out.print( Bytes.toLong( rowId) );
// System.out.println(" === "+ new String(rowId) );
if(i%1000000==0){
System.out.println( i );
}
rows.add(rowId);
}
System.out.print("rowid生成结束");
int pointer = 0;
Iterator<byte[]> rowKeyIter = rows.iterator();
int index = 0;
// System.out.println( );
while (rowKeyIter.hasNext()) {
byte[] tempRow = rowKeyIter.next();
// System.out.println( Bytes.toLong( tempRow ) );
rowKeyIter.remove();
if ((pointer != 0) && (pointer % splitKeysBase == 0)) {
if (index < splitKeysNumber) {
splitKeys[index] = tempRow;
System.out.println(" 中间值 "+ new String(tempRow) );
index++;
}
}
pointer++;
}
rows.clear();
rows = null;
return splitKeys;
}
/**
* 计算分区rowkey的测试程序
*
* @return
*/
public byte[][] calcSplitKeysTest() {
splitKeys = new byte[splitKeysNumber][];
// 使用treeset保存抽样数据,已排序过
TreeSet<byte[]> rows = new TreeSet<byte[]>(Bytes.BYTES_COMPARATOR);
for (int i = 1; i <= baseRecord; i++) {
byte[] rowId = rkGen.nextIdTest();
// System.out.print( " === "+ Bytes.toLong(rowId ) );
System.out.println(" === "+ new String(rowId)+" " );
rows.add(rowId);
}
int pointer = 0;
Iterator<byte[]> rowKeyIter = rows.iterator();
int index = 0;
// System.out.println( );
while (rowKeyIter.hasNext()) {
byte[] tempRow = rowKeyIter.next();
// System.out.println( Bytes.toLong( tempRow ) );
rowKeyIter.remove();
if ((pointer != 0) && (pointer % splitKeysBase == 0)) {
if (index < splitKeysNumber) {
splitKeys[index] = tempRow;
System.out.println(" 中间值 "+ Bytes.toString( tempRow) );
index++;
}
}
pointer++;
}
rows.clear();
rows = null;
return splitKeys;
}
public static void main(String[] args) {
HashChoreWoker hcw = new HashChoreWoker(5,2 );
// byte[][] bsk = hcw.calcSplitKeys();
// System.out.println( bsk );
byte[][] bskTest = hcw.calcSplitKeysTest();
System.out.println( bskTest );
}
}
分享到:
相关推荐
【大数据技术基础实验报告-HBase安装配置和应用实践】 这篇实验报告主要涵盖了HBase的安装、配置以及基本应用,这是大数据技术中一个重要的组件,它是一个分布式的、面向列的数据库,尤其适合处理大规模的数据。 1...
### HBase 安装与使用知识点详解 #### 概述 HBase 是一款构建于 Hadoop 之上的分布式、可扩展的大规模数据存储系统。它提供了类似 Google BigTable 的功能特性,非常适合处理海量数据和高并发读写需求的应用场景。...
在本文中,我们将详细讲解Hbase的安装过程以及基本操作,特别针对在Linux环境下使用清华大学镜像进行下载的情况。Hbase是一个分布式的、面向列的数据库,常用于大数据存储,是Apache Hadoop生态系统的一部分。以下是...
HBase安装与基本操作指南
通过以上步骤,我们可以确认HBase安装成功,并且可以进行基本的数据操作。随着需求的增长,可以进一步配置HBase的高级特性,例如设置复制、分区策略、优化查询性能等。在生产环境中,还需要关注HBase的监控和维护,...
在Linux环境下,构建基于Hadoop集群的Zookeeper和Hbase安装及配置是一项关键任务,因为这两个组件在大数据处理中扮演着重要角色。Hadoop生态系统中的HBase是一个分布式数据库,它建立在Hadoop集群的HDFS(Hadoop ...
内容概要:介绍了在 Linux 环境中安装 HBase 所需系统和 Java 的最低要求及其依赖关系 Hadoop 的部署步骤。本文提供了一种逐步设置和配置HBase的方法以及相关的基本CRUD操作指南,从而让用户可以在自己的机器上测试 ...
### HBase 安装与基本介绍 #### 一、HBase 概述 HBase 是一个分布式的、面向列的开源数据库,它旨在为结构化数据提供高效存储和检索服务。HBase 的设计灵感来源于 Google 的 Bigtable 论文,并且它作为 Apache ...
本资源主要涵盖了HBase的安装与使用,下面将详细介绍这两个方面。 一、HBase安装 1. **系统需求**:HBase通常运行在Linux环境下,因此首先确保你的服务器或开发环境是Linux。同时,需要安装Java Development Kit ...
在分布式大数据存储领域,HBase是一个非常...总之,HBase的安装和运维需要对Hadoop有深入理解,同时也需要熟悉分布式系统的基本原理。通过合理的配置和维护,HBase能够在大规模数据场景下提供高效、稳定的存储服务。
内容概要:本文详细介绍了HBase的安装步骤及其简单操作。首先是安装HBase的前提条件,...其他说明:本文不仅提供详细的安装步骤和操作示例,还深入探讨了HBase与Hive的不同之处,有助于更好地理解和应用这两个工具。
下面是基于标题“Hbase的shell基本操作”和描述“hadoop集群环境下hbase的shell基本操作命令”,结合给定的部分内容,所生成的详细知识点: 1. 进入HBase命令行: 通过命令`hbase shell`可以进入HBase的命令行界面...
【HBase的安装与配置】 HBase是一款基于Google Bigtable设计思想的开源NoSQL数据库,主要应用于大数据领域,尤其适合实时查询和分析大规模数据。在本次实验中,我们将学习如何在Linux环境下,以伪分布式的方式安装...
### Hadoop和Hbase安装使用教程 #### 一、准备工作 在正式开始Hadoop和HBase的安装之前,我们需要做一些准备工作。这些准备包括了安装必要的软件环境,例如虚拟机环境和SSH客户端,以及对虚拟机的基本配置。 ####...
在Windows上安装HBase 本文将指导您如何在Windows平台上安装HBase,包括配置详解。安装完成后,您将能够配置集群。 一、前提条件 ...但是,安装完成后,您将能够配置集群和使用HBase的强大功能。
#### HBase安装步骤及注意事项 ##### 版本选择与准备 - **版本匹配**:选择合适的HBase版本时,必须确认它与所使用的Hadoop、ZooKeeper以及JDK版本兼容。例如,HBase 1.4.6与Hadoop 2.7.6、ZooKeeper 3.4.6和JDK ...
#### 四、HBase安装 1. **下载并解压** - 下载HBase安装包并解压到与Hadoop相同的目录。 2. **配置** - **HBase环境变量** (`hbase-env.sh`): 设置Java路径。 - **HBase站点配置** (`hbase-site.xml`): 配置...