FML类型
索引:
- 概述
- 域表文件
- 域头文件
- mkfldhdr(32)工具
- 环境变量
- Falloc(Falloc32)
- Fsizeof(Fsizeof32)
- Fneeded(Fneeded32)
- Finit(Finit32)
- Fadd(Fadd32)
- Fchg(Fchg32)
- Fget(Fget32)
- Fcpy(Fcpy32)
- 输入/输出函数
- Fvftos(Fvftos32)
- Fvstof(Fvstof32)
1.概述
(1).基本概念
Field Manipulation Language(FML)或(FML32)可以定义多个有名字的域,它是一张属性和值的表。
支持的域数据类型有:short、char、long、float、double、string、carray。
FML(FML32)buffer通过一套API来管理,大约有60多个函数接口。
FML有较强大的功能,使用也很灵活。缺点是接口较复杂,有很多的处理函数,而且使用效率较VIEW等要慢。
(2).FML的基本组成部分
FML buffer的域通过域ID(数字)来访问。处理FML buffer至少需要如下四个部分:
- 域表文件。提供名字-数字映射;
- 域头文件。提供C程序一些生成的宏而不是数字来访问域;
- 环境变量FIELDTBLS(32)和FLDTBLDIR(32)定位表文件;
C语言接口:
库:libfml.a和libfml32.a;
头文件:fml.h和fml32.h;
处理16位到32位转换代码:fml1632.h。
(3).FML buffer的结构
一个域buffer有三部分组成:buffer头部、数据域和索引项。
(4).处理FML的流程
定义所有的域名字、对应的数据类型和数字标识。数字标识100以下为系统保留,对16位buffer,数字标识的范围是100-8191,32位buffer是100-33,554,431。
根据这些定义编辑一个域表文件。
使用mkfldhdr(32)生成域头文件。
编译应用程序,使用生成的头文件和fml.h(fml32.h),链接libfml.a(libfml32.a)。
正确设置环境变量FIELDTBLS(32)和FLDTBLDIR(32)。
2.域表文件
文件形式如下:
*base 100 # name number type flags comments ACCOUNT_ID 10 long - - ACCT_TYPE 11 char - - ADDRESS 09 string - - AMOUNT 16 float - -
文件中以#开头的行被忽略。
文件中以$开头的行也被忽略,但会被拷贝到后面生成的头文件。
文件以*base开头的行指出后面的域号的基本偏移。
每个域有以下部分组成:
- name:域的名字;
- rel-number:域的编号,它是一个相对当前base的数字;
- type:数据类型;
- flag:标志。保留;
- comment:注释。
该文件用来生成头文件,并在函数调用里使用。
3.域头文件
与域表文件对应的头文件形式如下:
/* fname fldid */ /* ----- ----- */ #define ACCOUNT_ID ((FLDID)8302) /* number: 110 type: long */ #define ACCT_TYPE ((FLDID)16495) /* number: 111 type: char */ #define ADDRESS ((FLDID)41069) /* number: 109 type: string */ #define AMOUNT ((FLDID)24692) /* number: 116 type: float */
4.mkfldhdr(32)工具
mkfldhdr(mkfldhdr32)工具将环境变量FIELDTBLS指定的域表文件对应生成一个C头文件,头文件的命名是在域表文件名后加后缀(.h)。缺省目标文件放在当前目录下,可以指定选项-d来指定生成的头文件存放位置。
使用举例:
FLDTBLDIR=/project/fldtbls; export FLDTBLDIR FIELDTBLS=maskftbl,DBftbl,miscftbl; export FIELDTBLS mkfldhdr maskftbl mkfldhdr DBftbl mkfldhdr miscftbl
5.环境变量
FIELDTBLS(FIELDTBLS32):以逗号分隔每个域表文件;
FLDTBLDIR(FLDTBLDIR32):以冒号分隔域表文件存放的路径列表。
注意列表中间不能插入空白字符。
6.Falloc(Falloc32)
使用malloc动态分配fielded buffer的存储空间并调用Finit进行初始化。
#include <stdio.h> #include <fml.h> FBFR *Falloc(FLDOCC F, FLDLEN V); #include <fml32.h> FBFR32 *Falloc32(FLDOCC32 F, FLDLEN32 V);
参数分别是域的个数和空间的字节数。
失败时返回NULL并设置全局变量Ferror。
失败原因:
- FMALLOC:malloc失败;
- FEINVAL:参数非法。
注意:该函数分配的空间只用于内部处理,不能用于tpcall()和tpacall()。
7.Fsizeof(Fsizeof32)
返回给定的FML buffer的大小。
long Fsizeof(FBFR *fbfr); long Fsizeof32(FBFR32 *fbfr32);
参数说明:
fbfr:buffer指针。
8.Fneeded(Fneeded32)
计算buffer需要的空间大小。
#include <stdio.h> #include <fml.h> long Fneeded(FLDOCC F, FLDLEN V); #include <fml32.h> long Fneeded32(FLDOCC32 F, FLDLEN32 V);
失败返回-1。
失败原因:
FEINVAL:非法参数。
9.Finit(Finit32)
用于清除一个存在FML buffer的内容以便重新使用它。对于使用Falloc和tpalloc分配的buffer该函数不是必须的。
int Finit(FBFR *fbfr, FLDLEN buflen); int Finit32(FBFR32 *fbfr, FLDLEN32 buflen);
参数说明:
bffr:要处理的buffer指针;
buflen:清理的空间字节数。
使用举例:
FBFR * fbfr; fbfr = (FBFR *) tpalloc(“FML”,NULL,Fneeded(5,200)); ... Finit(fbfr,Fsizeof(fbfr));
10.Fadd(Fadd32)
往buffer中的某个域填值,同一个域可以填多次,按下标0、1,2…依次存放。
int Fadd(FBFR *fbfr, FLDID fieldid, char *value, FLDLEN len); int Fadd32(FBFR32 *fbfr, FLDID32 fieldid, char *value, FLDLEN32 len);
参数说明:
fbfr:FML buffer指针;
fieldid:域ID号;
value:值存放的地址(char *类型)。当数据不是string或carray时要强制转化;
len:域长度。只对carray类型有效。
失败返回-1。
使用举例:
long db_id; ... (void)Fadd(reqfb, ACCOUNT_ID, (char *)&db_id, (FLDLEN)0); char *t_amts; ... if (Fadd(reqfb, SAMOUNT, t_amts, (FLDLEN)0) == -1) (void)printf(“Fadd failed with error: %d\n”, Ferror); char *t_amts; ... if (Fadd32(reqfb, SAMOUNT, t_amts, (FLDLEN32)0) == -1) (void)printf(“Fadd32 failed with error: %d\n”, Ferror32);
11.Fchg(Fchg32)
修改域的值。
int Fchg(FBFR *fbfr, FLDID fieldid,int occ, char *value, FLDLEN len); int Fchg32(FBFR32 *fbfr, FLDID32 fieldid,int occ, char *value, FLDLEN32 len);
参数说明:
fbfr:FML buffer指针;
fieldid:域ID号;
occ:域的下标。从0开始计算,-1表示增加值;
value:值的地址(char *);
len:域长度。只对carray类型有效。
失败返回-1。
若域指定下标当前没有值,则增加该下标的值。
使用举例:
char *t_amts; ... if (Fchg(reqfb,SAMOUNT, 0, t_amts,(FLDLEN)0) == -1) (void)printf(“Fchg failed with error: %s”,Fstrerror(Ferror));
12.Fget(Fget32)
取域的值。
int Fget(FBFR *fbfr, FLDID fieldid,int occ, char *value, FLDLEN *maxlen); int Fget32(FBFR32 *fbfr, FLDID32 fieldid,int occ, char *value, FLDLEN32 *maxlen);
参数说明:
fbfr:FML buffer指针;
fieldid:域ID号;
occ:域的下标。从0开始计算,-1表示增加值;
value:存放地址(char *);
maxlen:最大长度的指针,返回时被置为实际长度。
失败返回-1。
若当前空间不足以存放实际的值,函数并不截断数据,而是返回-1。
使用举例:
FLDLEN len2; long amount; . . . len2 = sizeof(amount); (void)Fget(transf, MID_INIT, 3, (char *) &amount, &len2);
13.Fcpy(Fcpy32)
进行FML buffer的拷贝。
int Fcpy(FBFR *dest, FBFR *src); int Fcpy32(FBFR32 *dest, FBFR32 *src);
失败返回-1。
函数认为两者都是FML buffer,当目标buffer足够大时进行复制。
14.输入/输出函数
int Fprint(FBFR *fbfr); int Fprint32(FBFR32 *fbfr);
以可读形式打印FML buffer的内容,输出到标准输出。
int Ffprint(FBFR *fbfr, FILE *iop); int Ffprint32(FBFR32 *fbfr, FILE *iop);
同上,但输出到指定的流中。
int Fextread(FBFR *fbfr, FILE *iop); int Fextread32(FBFR32 *fbfr, FILE *iop);
从流中读取数据到buffer中。
参数说明:
fbfr:buffer指针;
iop:输入/输出流。
格式的说明见ud部分的说明。
15.Fvftos(Fvftos32)
把FML buffer的数据拷贝到VIEW C结构中。
int Fvftos(FBFR *fbfr, char *cstruct, char *view); int Fvftos32 (FBFR32 *fbfr, char *cstruct, char *view);
参数说明:
fbfr:要拷贝的FML buffer指针;
cstruct:指向C结构数据的指针;
view:VIEW名称。
若FML中的域在结构中没有对应的项,则忽略。对于多记录的域,相应结构的域要是一个数组,如果buffer中的记录数小于结构中域数组的个数,则结构中多余部分置为null值。如果buffer记录数大于数组个数,则多余的值被忽略。
16.Fvstof(Fvstof32)
把VIEW结构中的数据拷贝到FML buffer中。
int Fvstof(FBFR *fbfr, char *cstruct, int mode, char *view); int Fvstof32(FBFR32 *fbfr, char *cstruct, int mode, char *view);
参数说明:
fbfr:FML buffer地址;
struct:C结构数据地址;
mode:拷贝模式。有以下可选值:
- FJOIN:把结构和FML buffer匹配的域中结构的值拷贝到结果buffer中;
- FOJOIN:执行FJOIN功能之外,也把FML buffer中其他内容拷贝到结果buffer 中;
- FUPDATE:执行FJOIN功能之外,也把FML buffer和结构的其他内容拷贝到结果buffer中;
- FCONCAT:把结构和FML buffer的全部内容都拷贝到结果buffer中。
view:VIEW名称。