
# 运行IoTDB UDF样例程序
#### UDF完整样例程序
可以参考[IoTDB UDF样例代码](https://support.huaweicloud.com/devg-lts-mrs/mrs_07_500041.html)章节。
#### 操作步骤
1. UDF注册。 
   注册一个全类名为"com.xxx.bigdata.iotdb.UDTFExample"的UDF可以按如下流程进行：
   1. 将项目打成Jar包，如果使用Maven管理项目，可参考以下章节的"构建Jar包"部分：
      - 开启Kerberos认证的集群请参考[注册UDF](https://support.huaweicloud.com/devg-lts-mrs/mrs_07_500043.html)。
      
      - 关闭Kerberos认证的集群请参考[注册UDF](https://support.huaweicloud.com/devg-lts-mrs/mrs_07_490041.html)。
       
   
   2. 以**root** 用户，登录IoTDBServer所在的节点，执行**su - omm** 命令切换到**omm** 用户，将[1.a]中的Jar包导入到目录"$BIGDATA_HOME/FusionInsight_IoTDB_\*/install/FusionInsight-IoTDB-\*/iotdb/ext/udf"下。
      ![](https://support.huaweicloud.com/cmpntguide-lts-mrs/public_sys-resources/notice_3.0-zh-cn.png)
      在部署集群的时候，需要保证每一个IoTDBserver节点的UDF JAR包路径下都存在相应的Jar包。可以通过修改IoTDB配置"udf_root_dir"来指定UDF加载Jar的根路径。
      
   
   3. 使用SQL语句注册该UDF，语法如下： **CREATE FUNCTION** \<UDF-NAME\> **AS** '\<UDF-CLASS-FULL-PATHNAME\>'
      例如，注册名称为"example"的UDF命令为：
      ```
      CREATE FUNCTION example AS 'com.xxx.bigdata.iotdb.UDTFExample'
      ```
      由于IoTDB的UDF是通过反射技术动态装载的，因此您在装载过程中无需启停服务器。
      ![](https://support.huaweicloud.com/cmpntguide-lts-mrs/public_sys-resources/notice_3.0-zh-cn.png)
      - UDF函数名称是大小写不敏感的。
      
      - 请不要给UDF函数注册一个内置函数的名字。使用内置函数的名字给UDF注册会失败。
      
      - 不同的JAR包中建议不要有全类名相同但实现功能逻辑不一样的类。例如UDF(UDAF/UDTF)：udf1、udf2分别对应资源udf1.jar、udf2.jar。如果两个Jar包里都包含一个"com.xxx.bigdata.iotdb.UDTFExample"类，当同一个SQL中同时使用到这两个UDF时，系统会随机加载其中一个类，导致UDF执行行为不一致。
        
   
   
   
   
2. UDF查询。 
   - UDF支持对的基础SQL语法为：
     - SLIMIT / SOFFSET
     
     - LIMIT / OFFSET
     
     - NON ALIGN
     
     - 支持值过滤
     
     - 支持时间过滤
      
   
   - 对齐时间查询。 UDF查询目前不支持对对齐时间序列"(Aligned Timeseries)"进行查询，当在SELECT子句中选择的序列中包含对齐时间序列时，会提示错误。
     
   
   - 带"\*"查询。 假定现在有时间序列"root.sg.d1.s1"和"root.sg.d1.s2"。
     - 执行**SELECT example(\*) from root.sg.d1**
       那么结果集中将包括"example(root.sg.d1.s1)"和"example(root.sg.d1.s2)"的结果。
       
     
     
     
     - 执行**SELECT example(s1, \*) from root.sg.d1**
       那么结果集中将包括"example(root.sg.d1.s1, root.sg.d1.s1)"和"example(root.sg.d1.s1, root.sg.d1.s2)"的结果。
       
     
     
     
     - 执行**SELECT example(\*, \*) from root.sg.d1**
       那么结果集中将包括"example(root.sg.d1.s1, root.sg.d1.s1)"，"example(root.sg.d1.s2, root.sg.d1.s1)"，"example(root.sg.d1.s1, root.sg.d1.s2)" 和" example(root.sg.d1.s2, root.sg.d1.s2)"的结果。
       
      
   
   - 带自定义参数输入的查询。 您可以在进行UDF查询的时候，向UDF传入任意数量的键值对参数。键值对中的键和值都需要被单引号或者双引号引起来。注意，键值对参数只能在所有时间序列后传入。例如：
     ```
     SELECT example(s1, 'key1'='value1', 'key2'='value2'), example(*, 'key3'='value3') FROM root.sg.d1;
     SELECT example(s1, s2, 'key1'='value1', 'key2'='value2') FROM root.sg.d1;
     ```
     
   
   - 查看所有注册的UDF。 **SHOW FUNCTIONS**
     
   
   
   
   
3. UDF卸载。 
   卸载UDF的SQL语法如下：
   **DROP FUNCTION** \<UDF-NAME\>
   卸载名称为"example"的UDF的命令为：
   ```
   DROP FUNCTION example
   ```
   
   
 
