开发者学堂课程【2020版大数据实战项目之 DMP 广告系统(第三阶段):Kudu 使用_Java API_扫描】学习笔记,与课程紧密联系,让用户快速学习知识。
课程地址:https://developer.aliyun.com/learning/course/678/detail/11783
Kudu 使用_Java API_扫描
在 kudu 的 Java API 这个环节当中介绍了创建表,也就是针对于表这个概念本身的操作,然后又介绍了如何插入数据,插入数据是针对表里面的数据来进行的操作,但是插入数据的方式,就是针对数据的操作有很多种,比如有增、删、改、查,、删和改就先不用说了,因为 Java 的 API 用的相对比较少,可能最多的还是使用 spark 的 API。这个时候直接向大家介绍如何查询数据,这个查询数据在非关系型数据库当中不是叫 find,也不是叫 query,也不是通过 SQL 进行查询,它们统一叫做扫描。其实在 h base 当中查询的操作也叫做扫描,接下来就来看查询如何进行。
一、扫描查询数据
大致还是三四个步骤。首先,要扫描是要先开一个扫描的对象,通过扫描对象来进行扫描,这也是面向对象的设计。接下来通过扫描器获取每一个 tablet server 里面 tablet 的数据。再去迭代 tablet 当中的数据,获取每一行数据,打印出来。但是在这之前,就是在获取数据之前应该先去设置一下投影,这个投影其实就是常说的谓词,也就是要查询哪一些列。如果要指定查询某一些列,有一些列可以不用查,明显会增快性能,所以投影是必须要设置的。
接下来,进入到 idea 当中,
@Test
def scan(): Unit = {
val KUDU_ MASTER =
“192.168.169.101:7051"
val kuduClient = new KuduClientBuilder(KUDU_ MASTER).build()
// 1.设置投影
import scala.collection. JavaConverters._
val projects = List("key"
, "value") .asJava
// 2. scanner 组装
Val scanner = kuduClient.newScannerBuilder( kuduClient.open Table( name = "simple"))
.setProjec tedcolumnNames(projects)
.build()
// 3.获取结果
while (scanner.hasMoreRows) {
//这个 Results 是一整个 tablet
val results = scanner.nextRows( )
while (results.hasNext) {
//这才是一条具体的数据
val result = results.next()
println(result.getstring(columnIndex=0
,result . getstring( columnIndex = 1))
}
}
}
}
创建一个新的方法,这个方法 Test 叫做 scan,然后 scan 创建出来以后直接把前两行拿过来,
val KUDU_MASTER ="192.168.169.101:7051"
val kuduClient = new KuduClientBuilder(KUDU_ MASTER).build( )
步骤很简单,第一步,设置投影,第二步,进行扫描的组织,scanner 组装,第三步应该去获取结果,这就是三个步骤。
先看 scanner 的组装,因为最直接还是通过 scanner 来进行查询的, scanner 对象呢通过 kuduClient 来获取,kuduClient 当中可以 new 一个 scanner builder,在 kudu 的 API 当中,其实提供的还是比较好的,Builder 是一个构建者模式,这个构建者模式用起来还是比较舒服的,这个时候它必须要求你提供一个 table 对象,是一个 kudu table 类型的,所以要去扫描哪个表是要先提供出来,通过 kuduClient.openTable 指定现在要扫描的 simple 这张表,提供这个数据以后,要去设置一下 ProjectedColumnNames,设置要去投影的那些列,如果是这样的话,就先去把这个列创建出来,它就是一个 projects,然后 List 后,就去指定,project 就是投影的意思,这个地方是 setProjectedColumnNames,然后要查 key 这一列,value 这一列也要,其次再去导入 scala 中的 collection 这个包下的 JavaConverts,然后下划线_,这个时候在这.asJava,因为这些都是 Java 的 API,如果它要接收一个 list,它接收的也一定是 Java 的 list,所以要给它转成 Java 的 list 才能传进来。
已经设置过投影了,就可以直接 build 了,除了设置投影这一个 API 以外,它有挺多东西可以设了,比如容错模式,包括也可以设置要访问的、要投影的 index 形式,就是第几列是要查的,现在使用的是 name 的形式。
scanner 有了以后就可以获取其中的数据了,while 一下,这个 scanner 其实也是一个迭代器模式,可以通过 scanner 来看一看它是否 hasMoreRows,就是它是否有更多的 Rows,如果有,就可以通过 scanner 去 nextRows,注意它不是 nextRow,而是 nextRows,它获取的是一次获取批量的数据,一次获取的是一整个 tablet 的数据,这个 Results 是一整个 tablet。
tablet 和 tablet server 是可以理解的,一个 tablet server 上是存放 tablet 的,一个 tablet server 可以存放多个 tablet,而这一次获取到的 results 是一个 tablet 里面的所有数据。
针对一个数据集,获取到的一整个 tablet 数据,可以再进行一次迭代,还是一个迭代器模式,通过 results 直接 hasNext,如果有下一个,直接 val 获取 result 这个 results.next 获取,这样就获取到具体的每一条数据了,这才是一条具体的数据,获取到具体的数据以后就可以 prinln,因为这是一个 no SQL 的 API,所以 result 当中要一个列一个列的获取数据,比如获取第一列是一个 string,那就把0传进来,然后可以在 result 获取第二列 string,可以把1传进来,获取这一行当中的第一条数据,就是第一个列的数据获取这一行当中的第二个列的数据,每个列的数据都是 string,这就是查询的扫描的这个代码。
接下来可以运行一下
这个时候已经获取到数据了,对应的是(A,1),数据已经获取好了,整个的扫描大概就是这样,其实就是一个 scanner,通过 scanner 获取一整个 tablet 的数据,然后再获取每一条的数据。