自动代码生成技术的发展现状与趋势

2018-09-10 12:30舒新峰王小银
西安邮电大学学报 2018年3期
关键词:构架代码框架

王 博, 舒新峰, 王小银, 陈 锐

(1. 西安邮电大学 计算机学院, 陕西 西安 710121; 2. 西安邮电大学 陕西省网络数据智能处理重点实验室, 陕西 西安 710121; 3. 西北大学 信息科学与技术学院, 陕西 西安 710127)

伴随着信息产业的不断深入发展,应用软件的需求和开发环境变得越来越复杂。传统软件开发方法暴露出新技术环境下的缺陷,比如开发周期漫长,工作重复较大,同时也给系统的演进和维护造成了很大的困难[1]。

与此同时,新软件开发思想和工具,也导致了软件工程方法论发生了深刻的变化,尤其是以OMG(object management group,对象管理组织)提出的模型驱动构架MDA(model driven architecture, 模型驱动构架)成为研究的主要方向。Frankel在其《应用MDA》一书中指出,“把宝贵的时间浪费在‘纸上谈兵’上是一种罪恶”[2]。当然也并非是说设计不重要,只是把一些无用的形式上的设计,甚至是开发完毕之后的设计而致使设计和实现脱节,纯属一种资源和时间的浪费。模型驱动构架使模型成为软件开发中的首要驱动力[3],模型不仅仅是程序员的文档,对软件系统的建模行为将直接驱动系统的开发[4]。

自动代码生成,即根据用户任务需求建模而自动生成源代码的程序或软件。自动代码生成深刻影响着软件开发的内容和形式。

(1) 减少重复的编码工作。自动代码生成减少很多不必要的重复代码的编写,基于模板或者模型,通过代码生成引擎,自动生成海量的代码,可以提高软件开发效率,优化软件开发过程。

(2) 代码生成风格上一致良好。不同的程序员在编写相同功能的模块时,最终编写的源代码会有很大的不同,但是通过自动代码生成的源代码,具有较好的一致性和规范性,同时也具有良好的可读性。

(3) 系统设计成为主导。整个开发过程,选择正确的模型至关重要。因此系统设计者的主要目光会放到模型的选择和系统业务逻辑的设计上。因此,系统的设计者会把较多的精力和实践花费在顶层设计上,提高系统的可用性和健壮性。

(4) 易于修改和升级。 自动代码生成的另外一个优势是可扩展性。在业务层次上,从长远来看,自动代码生成技术使得软件更容易修改和升级。

(5) 设计的连贯性。 自动代码生成鼓励程序员在编码体系内工作,其次,自动代码生成器良好的文档和可维护性为项目的维护和演化也提供了一致的结构和方法。

1 国内外发展状况

广义自动代码生成技术的用途是把高级语言编译成汇编代码、机器指令,是语言转换编译不可缺少的工具[5]。狭义自动代码生成技术是在软件开发过程中由经验而形成的一种软件工程技术,通过自动生成工具或者程序半自动或者全自动的生成应用系统的所用到的原始框架和代码,一般生成的是文本形式的源代码,进而编译部署运行。本文若不强调,特指在软件工程的项目开发中的狭义代码生成技术。

1.1 国外发展状况

代码生成技术可以分为如下的形式:代码重塑,内联代码展开,混合代码生成,局部类生成,层次化生成,全领域语言描述等[5]。

代码生成技术经过长期的发展和演进已经获得了很大的进步,技术实现上也有了长足的进展,一大批的工具随之而出现,尤其是基于模型构架模型驱动构架的代码生成技术出现了一大批的工具和成果。目前很多国外企业和相关机构都在专注于模型驱动构架的有关研究以及相应的工具开发。下面是国外的在模型驱动架构和自动代码生成方面的研究状况。

自动代码生成技术从20世纪末的萌芽阶段发展之今,已经趋于平稳和成熟,“自动代码生成”从1991年开始出现相关研究,2015年达到最热。模型驱动构架的研究始于20世纪70年代,和自动代码生成有着同步的研究趋势。图1为自动代码生成的研究热点走势,图2为模型驱动构架研究热点走势。从统计图中可以看出,代码生成在2010年后成为热点,近几年受机器学习和大数据技术发展而有所回落。(统计图中的纵轴代表研究成果,文中的数据统计于百度学术,数据截止于2018年3月20)。

图1 自动代码生成技术热点走势

图2 模型驱动构架研究热点走势

早在21世纪初,对象管理组织就宣布:模型驱动构架是其发展方向,动作快的厂商发布了具有模型驱动构架特性的产品,如OptimalJ,BorlandC#Builder Enterprise[2]。另外,一些中小厂商反而特别活跃,像Interactive Objects公司著名的ArcStyler工具,还有开放源码的AndroMDA等遵循对象管理组织标准规范的模型驱动构架工具已在一些项目中得到了广泛的运用,并取得了显著的成效。

除此之外,国外一些科研机构和高等学校在自动代码生成和基于模型驱动构架的自动代码生成方面也进行了广泛持久的深入研究。下面给出一些国外的自动代码生成的研究,文献[6-9]主要从模型驱动以及模型转换方面介绍自动代码生成引擎,文献[10]介绍了基于模板和可重用构件的自动代码生成方法和策略。文献[11-12]介绍了基于规则的代码生成策略。文献[13-15]介绍了基于注释的代码生成方法。其中文献[6]在基于基本准则的UML(unified modeling language,统一建模语言)类图的自动代码生成方面提出了设计方法和思路,并详细介绍了模型转换的规则和策略。文献[12]介绍如何通过IOPT(input-output place-transition,输入输出位置转换)Petri网实现ANSI C语言代码自动转化的工具。文献[8]给出了基于MDA的通过微软的ATL(active template library,动态模板库)技术转换生成MVC2(model view controller -2,模型视图控制器-2)的web应用生成引擎的实现方法。文献[9]详细介绍了模型驱动构架中各类不同模型比如PIM(platform independent model, 平台无关模型)到PSM(platform specific model,平台相关模型)以及PSM到代码的基于知识工程策略的转换规则和方法。文献[1]提出采用基于模型驱动构架的方法的XML(eXtensible markup language,可扩展标记语言)语言最大化自动生成代码的方法和策略,而且详细的给出了代码密度和代码获取量的计算方法。文献[16]介绍自主开发的一款基于动态框架的代码生成器,其使用SCT(specification configuration template, 规范配置模板)的方法来生成整个应用,而不仅仅只生成框架,并取得了不错的效果。文献[10]在支持构件化web工程中的构件重用的方面进行了深入的研究。文献[7]介绍了UML中的活动图和序列图的自动代码生成方法。文献[14]介绍了基于注释和注解的方法在J2EE技术中的代码生成的解决方案。文献[13,15]介绍了基于XDoclet的AOP(attribute oriented programming,面向属性的程序设计)方法。

1.2 国内发展状况

随着国外自动代码生成技术的发展,特别是其主要研究方向转化为以模型驱动的自动代码生成技术之后,国内的相关研究也逐渐开始起步。虽然缺乏坚实的理论支撑,但部分软件企业和高校科研机构也在不断跟进,取得了相应的成果。

20世纪80年代出现相关研究以来,到20世纪末自动代码生成技术发展缓慢,进展不大。但当时间跨入21世纪以后,尤其是随着模型驱动构架技术的引入以来,国内的自动代码生成技术有了较大幅度的发展,特别是自2005年以来,一直处于高峰研究状态。

自动代码生成是一个多领域多学科交叉的学科,涉及的面比较广。随着研究的不断深入,出现了越来越多与“代码生成”相关的研究点,形成了庞大的研究网络,该网络囊括:软件开发、编译器、模型驱动、嵌入式系统、设计模式和编译程序等领域的知识。

国内的软件企业在自动代码生成和模型驱动构架的研究和开发中也有不少成果,比如金蝶软件公司是首家实现支持模型驱动构架软件开发的商业工程工具金蝶EAS4.0,是一个基于模型驱动构架、采用“业务模型驱动的全自动化软件工厂”开发的企业应用平台[17]。楚凡科技是专业复杂软件及系统开发解决方案的供应商。为软件开发的整个生命周期提供集成的产品和专业化服务,楚凡科技工具Kant Studio集合了UML建模和数据库建模;实现数据库模型和UML模型的双向转换;实现代码和模型之间的迭代转换[18]。

一些中小企业和开源产品在上自动代码生成方面也有较好表现,开发了小型的代码生成器支持从模型或者模板到不同程序设计语言的转化。如动软.Net代码生成器是基于关系数据库元数据库的C#自动代码生成器,Codematic生成的代码基于面向对象思想和三层架构设计。BBOSS自动代码生成工具是一款为专有框架和平台生成前端、后端代码、WEB服务代码、SQL配置、IOC配置的可视化配置管理工具。Code Generator生成工具是基于Freemarker和Velocity模板生成代码的引擎,该生成器是根据关系实体的元数据来生成源代码。

国内的众多高校和研究机构也在代码生成、尤其是基于模型驱动骨架的代码生成软件工程也进行了长期的研究,取得了众多的成果。下面给出国内的在自动代码生成方面研究的典型问题,文献[19-25]在基于模型转换和代码生成方面给出了详细的介绍,文献[26-27]是基于对象关系映射方面的自动代码生成,文献[28-29]是基于模式的用户界面自动代码生成技术,其中文献[19-20]在逆向工程和程序流程图到自动代码生成提出一种基于图的生成算法,文献[21-22]在平台无关模型到平台相关模型,web用户界面建模和自动生成,用户界面代码自动生成方面进行介绍。文献[23]在模型驱动构架的模型转换方面提出一种基于规则的转化方法,文献[24]对MDA模型的转换方法进行了全面的分析。文献[25]对UML中的类图和顺序图自动生成C++语言代码提出了基于一种基于规则转化的生成方法。

目前相应的模型驱动理论研究还不够充分,仍旧需要国内学者共同努力,并开拓与开创新的研究领域和思路,形成系统的理论和方法,以期加速软件开发效率和对中小企业的软件开发提供持久的支持。

2 自动代码生成技术以及趋势

根据以往项目开发中的经验,自动代码生成器的设计应遵循一定的原则。

(1) 选择正确的模型。正确的模型对生成的质量是至关重要的。

(2) 不对自动生成的代码做任何手工修改。因为在开发过程中,需求会发生或多或少的变化,这样给后期代码重新生成造成很大困难。

(3) 要对生成的目标类型有全面的理解。在代码生成前,要对实体对象及其关系有全面的把握和理解。掌握好哪些是固定不变的业务逻辑,哪些是易变的业务,或者是生成的代码所在的层次,这样才能做到有的放矢。

(4) 明确代码生成器的输入源与目标代码之间的映射关系。明确输入源与目标代码之间的映射关系,是设计代码生成的关键所在。另外,输入源是否完整描述目标代码,也是生成代码易用性和效率的关键所在。

当前自动代码生成技术的方法主要有:基于模型的自动代码生成,基于模板的自动代码生成、基于对象关系映射、基于文档注释和基于动态代理的自动代码生成技术。由于目前使用广泛的自动代码生成主要有两大方法,一类是企业界的基于模板的代码生成方法,一类是理论界基于模型框架的代码生成方法,前者注重于时效性,往往能够生成某种类型的系统的框架80%或者以上的源代码,后者更注重于统一性,更注重于通用语言框架的代码生成。

2.1 基于模板的自动代码生成技术

基于模板的代码生成的基本原理是把软件的需求分成两部分,一部分是相对来说固定不变的部分,称为静态部分,另外一部分是根据外部输入变化的部分。比如实体中的属性的名称和方法的名称是变化的,这一部分通过特殊标记来替代。这样代码生成器引擎根据输入和模板文件,按照一定规则生成源代码,然后添加到项目文件中[30]。

前已述及,基于模板的代码生成是利用系统共性的需求(模板)和个性的需求(特定的外部输入),通过代码生成引擎来生成系统源代码的方法。基于模板的代码生成工具最困难的是明确区分输入和转化逻辑,也就是将元数据和具体业务规则进行分离,通过使用模板引擎技术,可将业务规则抽象到模板文件中,将元数据作为动态插入数据。基于模板的代码生成方法涉及分层和框架技术。

2.1.1 分层技术

分层技术在当前的软件开发中被广泛的使用。在软件开发过程当中,把具有不同过程的解决方案放置到不同的概念层上面,之后这整个层次形成一个不够密封的系统,其中每一个层次在级别上具有平等性[31]。分层的优点在于提高系统的灵活性和可复用性,能够在一定程度上提高软件开发的效率。

软件的分层随着用户的需求和软件体系结构的发展在逐层的演进,从20世纪80年代初的小型数据库的结构化程序设计的单层结构,基于服务端和客户端的双层结构,瘦客户端下的三层体系结构,以及将业务逻辑独立出来的分布式系统的四层和五层结构,见证了软件系统开发中的分层技术的发展趋势[32]。当前典型的Web系统的开发中,使用基于表示层、业务逻辑层、持久层三层体系结构。见下图3所示。

表示层数据呈现业务逻辑层业务处理持久层数据处理数据实体模型

图3典型的web分层体系结构

定义1(分层结构定义) 约定将n层构架的各层编号为1,2,…,n,其中层的编号越大,则越处于系统的高层。那么分层构架应该满足如下的规则:

(1) 第k层(1

(2) 如果p层依赖于q层,则p的编号一定大于q。

这个原则保证了层依赖的单向性,减少和降低了系统逻辑的复杂性,使得系统在提高功能高可复用性前提下易于控制。

定义2(分层对象模型) 基于分层体系的对象模型分成数据实体对象,持久层对象和业务逻辑层对象,每层的对象可以表示为一个n元组。

(1) 数据实体对象MO= (mo_id, mo_name, attr_set, op_attr),其中:mo_id, mo_name分别对应模型实体对象MO的唯一的标识和名称; attr_set 代表该实体的属性集;op_attr 代表对该属性的操作,一般对应该实体的可读和可写算子。

(2) 持久层对象PO = (po_id, po_name ,mo, dll_set) ,其中:po_id, po_name分别对应持久层对象PO的唯一的标识和名称;mo为持久层关联的模型层实体对象和实体对象集合;dll_set为持久层对应的操作集合,比如增删改查、分页、排序等。

(3) 业务逻辑层对象BO = (bo_id, bo_name, mo, bll_set),其中:bo_id, bo_name分别对应业务逻辑层BO的唯一的标识和名称;mo为持久层关联的模型层实体对象和实体对象集合;bll_set为业务逻辑层对应的操作集合,比如登录、注册、审核等业务逻辑层的功能。

基于模板的自动代码生成中,在进行模板生成或者模板定制的时候,往往根据不同的系统构架和元数据,采用分层的策略来进行生成,分别生成模型层、持久层、业务逻辑层和表示层的类型。这种策略结构清晰、目标明确,容易生成安全和质量有保证的系统源代码。

2.1.2 软件结构框架

对于软件结构框架,很难找到一个明确的统一的和公认的定义,常见的几个定义如下:

(1) 框架是一个系统全部或者部分的可复用设计,通常由一组抽象类和类之间的协作组成。

(2) “框架是一个能够被开发人员实例化的系统骨架”[33]。

(3) 软件框架是软件系统中的一组抽象构件以及构件间的接口所组成,在软件开发中开发人员可以根据实际需求对框架进行对象实例化与代码重构,从而快速形成一个“半成品”的应用系统程序,然后通过对业务流程的分析与设计从而完成整个应用系统的设计与实现[34]。

从上述定义可见,框架是一个“部分实现”的容器——一种软件体系结构,支持软件设计复用和实现复用的技术[33]。

当前主流的web框架有基于MVC结构的SSH(struts spring hibernate, SSH框架)框架,SpringMVC框架,基于Lucene的Compass框架,基于Spring的可插入的MVC(model view controller, 模型视图控制器)框架SWF(spring web flow, SWF框架)[35]。现有的主流Web框架基本是基于分层结构的模型视图控制器框架,在通用框架的作为基础平台的基础上,进行符合框架的代码定制。

2.1.3 自动代码生成策略

当前基于使用比较多得基于模板的生成技术主要用到Freemarker、XSLT(extensible stylesheet language for transformations,扩展样式表转换语言)技术和velocity技术,通过代码生成引擎将输入的数据模型替换模板文件中的可变部分来生成目标代码。由于模板文件基于文本易于定制和调整,结合成熟的模板语言可使代码生成过程更具灵活性,生成的代码质量更高。故其在中小企业中是应用最为广泛的一种方式[36]。在代码生成方案中,以下的三个元素是必须的。

(1) 模板:在生成的代码中,有些内容和逻辑是不变的,在基于模板的生成技术方案中,这些内容用模板存放,其中定义了生成代码的基本结构和逻辑。

(2) 元数据:元数据的本意是描述数据内容和结构,在代码生成技术中,元数据用于描述生成代码的内容。

(3) 业务规则:业务规则定义了生成系统的数据处理逻辑,主要是模块中的在持久层如何进行实体的持久,亦即基本的增删改查操作,在业务逻辑层定义构建在持久层基础上实体的业务逻辑操作。

基于模板的代码生成过程如图4所示。

图4 基于模板的自动代码生成过程

基于模板的自动代码生成的过程如下:首先对用户需求进行分析,进行初步的分析和设计,在实现阶段制定要采用的框架和何种分层结构,根据功能需求,设计相应的模板文件,并根据数据库或者元数据,使用代码生成引擎去生成程序的源代码。在生成的基础的源代码基础上进行代码调整和特定代码的添加,调试之后将代码部署到基础框架中。

2.2 基于模型驱动的自动代码生成及技术

基于模型驱动的自动代码生成及技术的方法是将要实现的软件系统抽象成模型,然后通过模型到代码的映射规则自动生成代码。现在流行的是基于模型驱动构架的代码生成。模型驱动构架的思想是以模型为驱动,由模型来生成或者编译成程序代码,实现软件需求。模型是模型驱动构架思想的核心。工作原理是先对用户的需求进行分析建立PIM(platform independent model, 平台无关模型),然后用相应的模型驱动构架转换工具和技术,将PIM转换成为PSM(platform specific model,平台相关模型),最后将PSM通过代码生成器生成特定平台上的目标代码[30]。

模型驱动构架的出现使得解决传统软件的开发问题并且以工厂化开发软件成为可能。模型驱动构架支持基于可视化模型驱动的软件设计、内容存储与交换,是一种基于模型的软件开发构架。其最终目标是把针对特定计算平台的编码工作,交由机器完成,从此将业务逻辑与实现技术结构。从而最大程度的提升软件开发效率和质量、降低开发成本、延长软件寿命,实现工厂化开发软件[37]。

2.2.1 模型层次结构

模型驱动构架中的模型组织分成四层结构[38],依次为M0到M3。层次结构上,上一层是下一层的基础,下一层是上一层的应用。M3是元-元模型,MOF(meta object facility,元对象机制)位于该层。MOF提供了定义M2层元模型所需要的更抽象一级的建模支持。MOF是M2层所有元模型的元模型,同时它也是自描述的,即MOF可以描述MOF元模型本身。在MDA框架中,M3层只有MOF这一个模型,它是MDA中最基础和核心的标准。为模型驱动构架中的所有模型/元模型提供统一的语言基础,为模型语言(元模型)定义提供公共标准。M2层为元模型,代表建议MOF之上的各种模型语言,提供对应不同领域的领域建模语言,为M1层的建模提供建模符号。M1层为模型层,是建模人员通常面对的模型,即采用模型语言为企业应用建立的模型描述。MDA的CIM(computation independent model ,计算无关模型)、PIM和PSM模型都位于该层,M0层为实例层,是M1层模型的实例化,对应模型的具体应用程序,是模型描述的最终目标。MDA四层元模型体系结构如图5所示。

图5 MDA四层元模型体系结构

2.2.2 MDA应用模型

MDA的应用模型包括计算无关模型CIM,平台无关模型PIM和平台特定模型PSM。 它们与实例模型中的实现特定模型ISM(implementation specific model, 特定实现模型)的关系如图6所示。

CIM计算无关模型用于描述系统需求、功能、行为和运行环境,也称为业务模型。PIM平台无关模型是抽出的业务逻辑,不包括与实现平台的技术相关的特定信息。PSM平台特定模型,从相应的PIM转换而来。ISM实现特定模型是PSM的实例化,包括PSM用于构建一个系统并使之运行的所有信息,如程序代码、装载规格、部署说明以及配置规范等,是一个可以实际运行的软件系统[39]。

图6 应用模型之间的转换关系

用户界面工程中的用户界面代码生成也是自动代码生成中重要的组成部分。MDA的应用框架,也类似于UI模型的卡梅隆(Cameloen)参考框架[28]。卡梅隆参考框架定义的四种模型分别是任务和概念、AUI(abstract user interface, 抽象用户界面)、CUI(concrete user interface, 具体用户界面)和FUI(final user interface, 最终用户界面)。卡梅隆参考模型的抽象界面独立于设备和平台,与任务特征相关,考虑输入输出的表示问题,是对界面的功能描述;具体用户界面模型与设备相关,与平台无关,考虑具体的实现问题,是界面模型的代码转化,转化时,引入具体设备特征,将抽象用户界面转化成具体用户界面,然后引入具体平台特征,再将具体界面模式转换为最终用户界面,具体参见图7。模型驱动构架的自动代码生成对用户界面的自动生成也具有指导意义。

任务和概念(Task and Concepts)抽象用户界面(AUI)具体用户界面(CUI)最终用户界面(FUI)

图7Cameleon参考框架

2.2.3 基于模型驱动的自动代码生成过程

基于模型驱动的自动代码生成的过程如下:首先根据用户的需求编写PIM,再根据PIM和目标平台编写转换规则,MDA代码生成引擎根据转换规则自动将PIM转化成PSM,最后将PSM转换成代码。MDA通过两次模型转换和代码生成技术提高软件开发的效率,并使得系统具有较好的可一致性和可复用性。基于模板的代码生成过程参见图8。

图8 基于模型的代码生成过程

2.2.4 两者的优缺点和融合

基于模板的自动代码生成具有较高的灵活性,定制和开发较为容易,提高了软件开发的可复用度。但也有其确定,模板化的程序可读性差,生成的代码依赖于某种语言和框架,移植性差。在其他类似项目中使用,如果采用的框架不同或语言不同,需要重新构建新的自动代码生成引擎。

模型驱动构架相比于传统的软件开发方式和基于模板的自动代码生成方式,具有开发效率高、可维护性可扩展性强的特点,系统具有良好的可移植性[40]。但是模型驱动构架也存在一些缺点:虽然模型驱动构架的目标远大,但是实现模型驱动构架的技术模糊,基础规范MOF和UML都存在着语义不精确、语言不可执行的问题;另外构成平台的元素还不是很确定,这就导致从系统的抽象模型到精确模型的转化可能包括多个阶段,而且每个阶段相对于前一阶段可以说成是平台相关的。那么从这个意义上来说,PIM到PSM的转换是模糊的[37]。

基于模板的自动代码生成和基于模型的自动代码生成两者各有其优点和缺点,前者更注重于时效性,后者更注重于通用性,两者之间有一道鸿沟不可逾越。基于模板的代码生成可以认为更关注类似PSM到代码的生成,基于模型的自动代码生成更关注于模型的转换和平台无关模型到平台相关模型之间的转化。因此,可以在两者之间架起一座桥梁,融合现有的基于模板的技术和基于模型的代码生成技术。

2.3 基于对象关系映射的代码生成

基于对象关系映射的代码生成主要是基于面向对象和关系数据库技术的结合体。如:Microsoft的.NET框架,JAVA开源ORM(object relation mapping,对象关系映射)框架[41]。典型的JAVA ORM工具是hibernate。hibernate是对JDBC(java database connectivity,Java数据库连接)数据库技术进行轻量级的对象封装,使开发人员能方便的操作各种类型的数据库代码,利用Hibernate工具,使得JAVA实体类、hbm(hibernate mapping,hibernate 映射)映射文件、数据库表之间可以相互转化,但是缺乏进一步对实体持久性和业务逻辑以及视图层代码的生成。其次,可以通过对关系数据库元数据的分析,结合模板或者模型的方式来生成持久层和业务逻辑层的代码。

2.3.1 阻抗不一致

对象和关系模型存在着映射不一致的鸿沟,关系模型有深厚的以集合论为指导的数学理论基础,使用二维表来存储数据,表和表之间通过外键来描述实体之间的关系。对象模型是面向对象程序设计中的一种开发范型,对象模型通过继承、封装、多态来表示复杂实体的关系,对象之间的通信方式时候发消息,面向对象模型关系如图9所示。在软件开发过程中,广泛的使用面向对象的程序设计作为开发的范型,实体的存储主要是以当前主流的关系数据库为数据存储机制。对象建模和关系建模之间存在一条巨大的鸿沟,因为产生所谓的对象关系阻抗不一致问题,ORM就为解决这种问题而诞生。

图9 面向对象模型图

2.3.2 对象模型和关系模型

定义3[42]一个对象类的定义为O(A1,…,An,M1,…,Mn), 其中,Ai(i=1,2,…,n)为对象类的属相,定义域在Di上;Mi(i=1,2,…,k)为类的方法,返回值定义在域Di上。

定义4[42]关系R是笛卡尔积D1×D2×…×Dn的一个子集,D1×D2×…×Dn是所有的有序的n元组〈d1,d2,…,dn〉的集合,其中d1∈D1,d2∈D2,…,dn∈Dn,D1×D2×…×Dn称为关系R的域。关系模式的一般形式可表示为R=〈U,D,DOM,∑〉,其中U为组成关系R的全部属性集合,D为域的集合,DOM为U和D间的映射,∑为U上的一组依赖关系。

定义5[42]映射函数F是满足下列条件的函数:F的定义域为对象所有实例的集合,设为I;F的值域为关系数据库中的所有视图的幂集,设为Π,对一个对象实例,o∈I,其所有的方法与属性的集合为S。V∈Π,即V为若干视图的集合。

2.3.3 基于对象关系映射的代码生成方法

对象关系映射的关系对应如下,面向对象中的类模型对关系模型中的表,面向对象中的对象模型对应关系模型中的行记录,面向对象中类的属性对应关系模型中的表关键字,面向对象中类的关系对用关系模型中的对象[27,30]。如下图10所示。

图10 ORM映射规则

对象关系映射自动生成引擎的生成代码主要是如下方法:根据软件功能需求建立实体关系图,或者根据原有企业的遗产系统读取实体关系,根据实体之间的关系,通过代码生成引擎生成相应的模型层类代码、持久层类;更进一步可以生成业务逻辑层框架和代码和基本的展示层代码。

2.3.4 基于对象关系映射的代码生成优缺点

优点:对于实体关系非常明确的领域模型,或者已有数据库遗产系统,可以非常容易的映射成面向对象的领域模型,生成不同层次的代码,提高效率。

缺点: 生成模型相对来说比较单一,生成结构有时过于复杂,持久效率在关联复杂的情况比较低下。

对于实体关系模型不确定的问题,难于进行实体关系映射,生成结构相对单一,生成代码比较有限。

2.4 基于文档注释解析的自动代码生成

这种方式也属于混合代码生成方式。该生成方法查找特别格式的注释,然后生成代码所需要的一些新源码来填补这些注释区域,换言之这种代码生成是通过解析代码文件中的注释语句来生成代码,将控制代码生成和模板处理的标签作为内联注释嵌入到源文件代码中,消除了同步多个相关文件和控制文件的需要。混合代码生成用途广泛,例如@XDoclet可以通过在Java源文件中的一些特殊的注释信息,自动生成配置文件、源代码等,WEB、EJB(enterprise java bean,JAVA商业应用组件)的部署描述文件,为struts的struts-config.xml配置文件、JavaScript校验等。比如javadoc可以通过文档的注释生成API的设计说明书,tomcat可以根据JSP生成对应的servlet。这种方式的优点是对于业务逻辑特殊或者特别复杂的问题,把复杂的业务逻辑部分单独来写,特定的可替换的部分用文档注释来书写,代码生成引擎根据特定规则对文档注释进行转换。但描述这类文件较复杂,缺乏统一通用性[43]。

文档注释是定义在类中的特殊注释,这些文档注释用来向代码中的类、方法以及属性之类的语言特征添加元数据,随后通过文档和代码生成引擎,利用这些额外的元数据来生成诸如描述符和源代码之类的相关文件。注解(Annotation),也叫元数据。一种代码级别的说明。主要用于元数据生成文档和代码二次生成和以及编译检查。当前注解和文档注释被广泛的使用,以生成大量的配置文件和程序源代码。

源码上的标记,无论是文档注释还是注解,对于项目开发者来说,都有如下的优势:通过实际的代码,合并有用的元数据,分离编码和某些领域相关语义的问题,使得设计和开发者能够容易的重用存在的代码和功能,这些技术对于软件系统的维护和支持都有帮助。

2.5 基于代理的动态类的代码生成

较少有文献把基于代理的动态类的代码生成认为是自动代码生成技术,因为这种代码生成并不真正生成源代码,而是通过代理技术来动态的生成类的方式,也就是说,在程序运行时创建类的字节码或机器码,并且在程序运行或者解释期间动态生成、动态加载并调用执行。JavaEE技术中使用动态代理类的场合比较多,比如Spring的AOP(aspect oriented programming, 面向切面编程)技术。Java原生代理实际上是创造了一个实现了所有给定接口的类,并在调用接口的方法的时候使用反射达到代理效果。动态代理提供了一种动态执行程序组件的方法,通过动态代理实现业务控制器对软件构件的调用。动态代理是一种特殊的代理模式,其代理对象是在程序运行期间动态创建的。它的主要特点是不需要定义代理对象、程序代码高度抽象以及对象之间耦合弱的特点。动态代理技术比如JAVA的动态代理Proxy,CGLIB代码生成库等提供了动态代理类的生成。

2.5.1 AOP和动态代理

AOP(aspect oriented programming, 面向切面编程),通过预编译方式和运行期动态代理实现程序功能的统一维护的一种技术。AOP是OOP(object oriented programming,面向对象程序设计)的延续,是软件开发中的一个热点,是函数式编程的一种衍生范型。利用AOP可以对业务逻辑的各个部分进行隔离,从而使得业务逻辑各部分之间的耦合度降低,提高程序的可重用性,同时提高了开发的效率。代理类在程序运行时创建的代理方式被称为动态代理。也就是说,这种情况下,代理类并不是在代码中定义的,而是在运行时根据代码中的“指示”动态生成的。相比于静态代理,动态代理的优势在于可以很方便的对代理类的函数进行统一的处理,而不用修改每个代理类的函数。

2.5.2 动态生成技术CGLIB

CGLIB是一个强大的、高性能的代码生成库,广泛的应用与AOP中,用于提供方法的拦截操作。CGLIB代理通过对字节码的操作,为对象引入间接级别的操作。CGLIB低层使用了字节码操作框架ASM来生成新的类。ASM框架是一个Java字节码操纵框架。它可以直接以二进制形式动态地生成stub类和其他代理类,或者在装载时动态地修改类。

2.6 自动代码生成方法之比较

不同的自动代码生成技术有其使用的场合,有其特定环境下的优点和缺点,表1从自动代码生成方法的输入输出、使用场合、优缺点和相关技术,给出纵横向的比较。

表1 自动代码生成方法之比较

2.7 自动代码生成技术发展趋势

当前自动代码生成主要采用的是基于模型的自动代码生成和基于模板的自动代码生成,两者趋于融合。未来可以根据计算机和人类处理问题的特点,采用人机协同的开发方法,根据实体业务的复杂性和需求变化频度进行生成,划分成基础框架部分、全生成部分、半自动生成部分和全手工部分,构建弹性、高可用性和高可复用性的自动代码生成引擎。今年,CCF将基于人工智能的软件开发构造、代码生成及技术和基于人工智能的软件分析、测试、验证与诊断技术以及智能人机接口软件的设计和实现技术作为未来研究的重要技术方向;其次,更细粒度的智能代码生成模型与自动代码生成仍然需要加大研究的力度,以适应不断变换发展的社会需求。

3 结语

本文主要讨论了代码生成技术,尤其是基于MDA的自动代码生成技术的国内外研究和应用现状,详细分析了当前自动代码生成技术所使用策略和方法。较多类似的管理系统,如高校的排课管理系统[44]中后台管理的大部分代码都可以采用自动代码生成技术完成。通过对实现方法有效性的相应验证可知,虽然随着软件工程新方法论的提出取得了一定的成果,但是,自动代码生成技术还有很多不成熟之处。比如:基于模型驱动构架的转换工具和方法还不尽成熟,缺乏成熟系统的理论支持;基于模板和规则的方法只能对于特定问题域的系统方法有效,对于业务逻辑复杂的系统还是缺乏行之有效的方法。

猜你喜欢
构架代码框架
有机框架材料的后合成交换
框架
建筑安装造价控制核心要点构架
K-框架和紧K-框架的算子扰动的稳定性
急诊PCI治疗急性心肌梗死的护理探索构架
创世代码
创世代码
创世代码
创世代码
高可靠全平台ICT超融合云构架的设计与实现