[UDF系列]如何创建InterBase UDF

原创 2003年06月25日 15:32:00

[UDF系列之五]:如何创建InterBase UDF<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" />

by Paul McGee (c) Borland Internation Inc.

Warton

[概述]:

用户定义函数(UDF)是一种采用编译语言编写的函数,是用户为执行自定义的功能和常用的任务面设计的。UDF 允许程序员模块化一个数据库应用程序,并能嵌入到数据库以增强数据库自身的功能。UDF 也总是在数据库服务器端执行。这可以减少网络通信量。

UDF可以执行事务比如获得服务器上可用硬盘空间,清理字符串的空格,为一系列值计算标准偏差等等。UDF能完成任何功能只要编程语言能够表达出来。这种编程语言能常是在C和C++之间选择(当然,用户可以用其它语言,比如pascal 译者注)。

UDF在提供SQL语言不能处理的功能、查询、更新数据库,以及为异源客户工作站提供通用函数方面非常有效。

与其它功能相比,使用UDF要花费一些代价。这主要表现在两方面:第一,在UNIX或VMS平台,UDF是模块化AST程序,这意谓着当UDF在执行时,没有其它的存取操作可以发生。这就要求我们尽量使UDF尽可能的小和有效率。第二,如果数据库服务器崩溃,你需要将数据转移到另一台机器上。你必须首先在新的服务器上安装UDF。如果在相同的操作系统下,这并不难。但是当转移到另一操作系统时,你只少需要编译一遍UDF库的源代码。

[UDF示例]:

     InterBase包含几个内置SQL 函数:UPPER,GEN_ID,CAST 。UPPER将一个字符串转为大写。GEN_ID生成一个唯一长整型值,因为一个特殊的生成器已经在数据库中定义。这在生成主键时是非常有用的,比如客户编号或职员编号。CAST将一种类型列转化为另一种类型的列。

    InterBase 也提供了另外一些UDF的源代码,在examples目录下。它们包含在udflib.c文件中。这里定义的UDF有:lower, strcat, substr, trim, trunc, doy, moy, dow, sysdate, add2, mul, fact, abs, maxnum, sqrt, blob_linecount, blob_bytecount, substr_blob。Lower是将字符串转化为小写串。Strcat连接两个字符串。Substr返回字符串的一部分。Trim清空字符串中的空格。Trunc返回删节后的串。doy(day of year),moy(month of year),dow(day of week)。Sysdate返回当前日期以字符串的形式(“mmm-dd-yyyy”).add2将两整数相加在一起。Mul将两double数相乘.maxnum返回两数中较大者。Sqrt为取平方。blob_bytecount返回blob的大小。Substr_blob,取blob的一部分文本。

    我们将增加几个新的UDF:rtrim, left, right, swapcase, imonth, iday, iyear。Rtrim去掉字符串右边的空格。Left返回一个输入串前n个字符的串。Right则是返回右过n个字符的串。Swapcase将小写转大写并将大写转小写。imonth返回月份的值(1-12)。Iday返回day的值(1-31)。Iyear返回年的值如:2002。

[编写UDF]:

    一旦你编写的UDF,你必须创建一个动态链接库,以便上UDF可以使用。然后你必须在数据库中定义它。

在数据定义语言中定义 UDFs 非常简单,基本的语法是:

DEFINE EXTERNAL FUNCTION name [<datatype> | CSTRING (int)

                [, <datatype> | CSTRING (int) ...]]

                RETURNS {<datatype> [BY VALUE] | CSTRING (int)}

                ENTRY_POINT "<entryname>"

                MODULE_NAME "<modulename>" ;

Name是指函数的名称,它可达到31个字符长。第一个datatype是输入参数。Datatype指标准的interbase数据类型:INTEGER, CHAR, VARCHAR等。或者,你可以使用CSTRING这个C风格没用结束的字符数组。Entry_point指实际的函数名。在InterBase提供示例中,SQL函数名是lower而实际函数名在udflib.c中为fn_lower_c。模块名指的是函数被编译后的输出库名。例如:这里用SQL 定义函数lower和substr。

        DEFINE EXTERNAL FUNCTION lower

                VARCHAR (256)

                RETURNS CSTRING (80)

                ENTRY_POINT "fn_lower_c" MODULE_NAME "funclib";

       

        DEFINE EXTERNAL FUNCTION substr

                CSTRING (256), SMALLINT, SMALLINT

                RETURNS CSTRING (80)

                ENTRY_POINT "fn_substr" MODULE_NAME "funclib";

为了将函数加入到函数库中,在NT上使用Borland C++,我们应该让lib模块有有一个本地的拷贝:

 implib mygds32.lib /interbas/bin/gds32.dll

然后连接必要的选项生成我们新的库funclib.dll。

 

bcc32 -v -a4 -DWIN32 -tWM -tWCD -efunclib.dll udf.c mygds32.lib

为了在本地使用DLL,它必须在BIN目录下(或你环境变的路径中)。如果要在远程使用,它必须在能运行InterBase服务的用户的环境变量路径之中,默认情况下,它在系统账户的PATH中。

[使用UDF]:

一但编译,连接,定义之后,一个UDF就可以在SQL 语句中使用了。

它们可以做如下使用:定义计算后字段做为表定义的一部分,在view定义中中做为列表达式或在存储过程和触发器中做为SELECT, INSERT, UPDATE, DELETE操作的一部分。

例如,使用计算结果做为字段:

        CREATE TABLE name ( FIRST_NAME VARCHAR(20), LAST_NAME VARCHAR(20),

                FULL_NAME_UPPER COMPUTED BY

                (upper(FIRST_NAME) | " " | upper(LAST_NAME)));

view中做为一个列表达式:

        CREATE VIEW upper_names (FIRST_NAME, LAST_NAME) AS

                SELECT upper(n.first_name), upper(n.last_name) FROM name n;

在选择操作中:

        SELECT substr(n.FIRST_NAME, 2, 4) FROM name n WHERE

                upper(n.LAST_NAME) = '<?xml:namespace prefix = st1 ns = "urn:schemas-microsoft-com:office:smarttags" />MOORE';

在插入操作中:

        INSERT INTO name (FIRST_NAME, LAST_NAME)

                VALUES (rtrim(:new_fname), rtrim(:new_lname));

在更新操作中:

        UPDATE name SET LAST_NAME = rtrim(:new_lname) WHERE

                upper(n.LAST_NAME) = 'JONES';

在删除操作中:

        DELETE FROM name WHERE left(LAST_NAME, 3) = 'SMI';

 

 

本主来自:MER Systems Inc..  http://www.mers.com

 

[UDF系列]如何编写InterBase UDF 之一

如何编写InterBase UDF(作者:Gregory Deatz - Hoagland, Longo, Moran, Dunst & Doukas)warton 译 译者叙:由于InterBase...
  • warton
  • warton
  • 2003年06月25日 15:31
  • 1111

[UDF系列]如何编写InterBase UDF 之二

(接上一篇)如何编写InterBase UDFwarton译怎么编写字符串和日期型处理函数的UDF呢? 下面编写一个“Left“函数    内存分配问题:              如果你使用IB(I...
  • warton
  • warton
  • 2003年06月25日 15:32
  • 1061

[UDF系列]如何编写InterBase UDF 之三

(接上一篇)如何编写InterBase UDFwarton译(前面讲了在windows下编写UDF)编写Linux/Unix平台的UDF(译者注:原用大量篇幅讲述了linux下的SO(shared o...
  • warton
  • warton
  • 2003年06月25日 15:33
  • 1236

[UDF系列]如何编写InterBase UDF

译者叙: 由于InterBase性能方面表现突出,并且它是开源和跨平台的,有很多使用Delphi,C++Builder的程序员开始采用它做为其后数据库平台。但是InterBase的中文资料简直太少了...
  • SeekMyself
  • SeekMyself
  • 2013年02月25日 13:09
  • 1410

自定义UDF函数应用异常

定义函数PlatformConvert: 实现传入hive表中string类型字段,通过查询中间表,返回int类型主键id值 publicclass PlatformConvert...
  • zls_01
  • zls_01
  • 2017年08月19日 20:19
  • 151

用Java编写的第一个UDF

准备: 1.在Hive中以创建t_emp表,并且put数据如下: 2.在Eclipse 中搭建UDF编写环境,导入Hive相关包 实现: 1.编写一个UDF类,继承UDF package co...
  • qq_26624661
  • qq_26624661
  • 2017年09月04日 21:34
  • 367

hive udf开发以及永久注册udf函数

网上大部分资料显示注册 hive udf 函数大体有两种方法: 第一种、创建临时函数。如在hive CLI执行下面命令: hive> add jar helloudf.jar; hive> cre...
  • zhoujianfeng3
  • zhoujianfeng3
  • 2015年01月23日 10:39
  • 2632

udf打jar包

1. 编译 javac -cp /opt/hadoop/hadoop-core-1.1.1.jar:/opt/hadoop/hive/lib/hive-exec-0.10.0.jar  ToWeek....
  • godspeedlaile9
  • godspeedlaile9
  • 2013年12月09日 16:18
  • 979

Hive UDF调试打印的方法

日志的打印 导入用到的包 import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory;   ...
  • conggova
  • conggova
  • 2017年08月26日 19:16
  • 328

UDF的调试方式-debugview

  • zgqtxwd
  • zgqtxwd
  • 2008年04月30日 12:38
  • 310
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:[UDF系列]如何创建InterBase UDF
举报原因:
原因补充:

(最多只允许输入30个字)