| Shen's profileshen universalPhotosBlogLists | Help |
|
|
August 01 流
Java文件操作大全本文汇集常用文件操作方法,包括文件的建立/检查与删除,目录的建立/检查与删除,取出目录中文件,文件属性的取得,逐行读取数据等等。
文件的建立/检查与删除<%@ page contentType="text/html;charset=gb2312"%> 目录的建立/检查与删除<%@ page contentType="text/html;charset=gb2312"%> 如何在JSP中处理虚拟目录<%@ page contentType="text/html;charset=gb2312"%> 文件属性的取得<%@ page contentType="text/html;charset=gb2312"%> 取出目录中文件的方法<%@ page contentType="text/html;charset=gb2312"%> 判断是否为空白文件<%@ page contentType="text/html;charset=gb2312"%> 一行一行读取数据<%@ page contentType="text/html;charset=gb2312"%> 略过文件中的字符不读取<%@ page contentType="text/html;charset=gb2312"%> 将数据写入文件<%@ page contentType="text/html;charset=gb2312"%> 将写入文件的数据分行<%@ page contentType="text/html;charset=gb2312"%> 如何将数据追加写入到文件<%@ page contentType="text/html;charset=gb2312"%> July 23 Struts常见错误汇总以下所说的struts-config.xml和ApplicationResources.properties等文件名是缺省时使用的,如果你使用了多模块,或指定了不同的资源文件名称,这些名字要做相应的修改。 1、“No bean found under attribute key XXX” 在struts-config.xml里定义了一个ActionForm,但type属性指定的类不存在,type属性的值应该是Form类的全名。或者是,在Action的定义中,name或attribute属性指定的ActionForm不存在。 2、“Cannot find bean XXX in any scope” 在Action里一般会request.setAttribute()一些对象,然后在转向的jsp文件里(用tag或request.getAttribute()方法)得到这些对象并显示出来。这个异常是说jsp要得到一个对象,但前面的Action里并没有将对象设置到request(也可以是session、servletContext)里。 可能是名字错了,请检查jsp里的tag的一般是name属性,或getAttribute()方法的参数值;或者是Action逻辑有问题没有执行setAttribute()方法就先转向了。 还有另外一个可能,纯粹是jsp文件的问题,例如会指定一个id值,然后在循环里使用这个值作为name的值,如果这两个值不同,也会出现此异常。(都是一个道理,request里没有对应的对象。) 3、“Missing message for key "XXX"” 缺少所需的资源,检查ApplicationResources.properties文件里是否有jsp文件里需要的资源,例如: 这行代码会找msg.name.prompt资源,如果AppliationResources.properties里没有这个资源就会出现本异常。在使用多模块时,要注意在模块的struts-config-xxx.xml里指定要使用的资源文件名称,否则当然什么资源也找不到,这也是一个很容易犯的错误。 4、“No getter method for property XXX of bean teacher” 这条异常信息说得很明白,jsp里要取一个bean的属性出来,但这个bean并没有这个属性。你应该检查jsp中某个标签的property属性的值。例如下面代码中的cade应该改为code才对: 5、“Cannot find ActionMappings or ActionFormBeans collection” 待解决。 6、“Cannot retrieve mapping for action XXX” 在.jsp的标签里指定action='/XXX',但这个Action并未在struts-config.xml里设置过。 7、HTTP Status 404 - /xxx/xxx.jsp Forward的path属性指向的jsp页面不存在,请检查路径和模块,对于同一模块中的Action转向,path中不应包含模块名;模块间转向,记住使用contextRelative="true"。 8、没有任何异常信息,显示空白页面 可能是Action里使用的forward与struts-config.xml里定义的forward名称不匹配。 9、“The element type "XXX" must be terminated by the matching end-tag "XXX".” 这个是struts-config.xml文件的格式错误,仔细检查它是否是良构的xml文件,关于xml文件的格式这里就不赘述了。 10、“Servlet.init() for servlet action threw exception” 一般出现这种异常在后面会显示一个关于ActionServlet的异常堆栈信息,其中指出了异常具体出现在代码的哪一行。我曾经遇到的一次提示如下: java.lang.NullPointerException at org.apache.struts.action.ActionServlet.parseModuleConfigFile(ActionServlet.java:1003) at org.apache.struts.action.ActionServlet.initModuleConfig(ActionServlet.java:955) 为解决问题,先下载struts的源码包,然后在ActionServlet.java的第1003行插入断点,并对各变量进行监视。很丢人,我竟然把struts-config.xml文件弄丢了,因此出现了上面的异常,应该是和CVS同步时不小心删除的。 11、“Resources not defined for Validator” 这个是利用Validator插件做验证时可能出现的异常,这时你要检查validation.xml文件,看里面使用的资源是否确实有定义,form的名称是否正确,等等。 July 21 拨开SOA的面纱【导读】最近半年以来,在企业级应用开发领域,谈论最多的一个词,恐怕非SOA(Service-Oriented Architecture,面向服务架构)莫属。那么SOA究竟拥有什么样的魔力,能够让众多的软件厂商对他趋之若骛,掀起新的一轮企业架构浪潮。让我们在本文中一探SOA的究竟。 什么是SOA? SOA是一种架构模型,它可以根据需求通过网络对松散耦合的粗粒度应用组件进行分布式部署、组合和使用。服务层是SOA的基础,可以直接被应用调用,从而有效控制系统中与软件代理交互的人为依赖性。 SOA的关键是“服务”的概念,W3C将服务定义为:“服务提供者完成一组工作,为服务使用者交付所需的最终结果。最终结果通常会使使用者的状态发生变化,但也可能使提供者的状态改变,或者双方都产生变化”。 Service-architecture.com将SOA定义为:“本质上是服务的集合。服务间彼此通信,这种通信可能是简单的数据传送,也可能是两个或更多的服务协调进行某些活动。服务间需要某些方法进行连接。所谓服务就是精确定义、封装完善、独立于其他服务所处环境和状态的函数。” Looselycoupled.com将SOA定义为:“按需连接资源的系统。在SOA中,资源被作为可通过标准方式访问的独立服务,提供给网络中的其他成员。与传统的系统结构相比,SOA规定了资源间更为灵活的松散耦合关系。” Gartner则将SOA描述为:“客户端/服务器的软件设计方法,一项应用由软件服务和软件服务使用者组成……SOA与大多数通用的客户端/服务器模型的不同之处,在于它着重强调软件组件的松散耦合,并使用独立的标准接口。” Gartner相信BPM和SOA的结合对所有类型的应用集成都大有助益??“SOA极大的得益于BPM技术和方法论,但是SOA面临的真正问题是确立正确的企业意识,即:强化战略化的SOA计划(针对供应和使用)并鼓励重用。” 虽然不同厂商或个人对SOA有着不同的理解,但是我们仍然可以从上述的定义中看到SOA的几个关键特性:一种粗粒度、松耦合服务架构,服务之间通过简单、精确定义接口进行通讯,不涉及底层编程接口和通讯模型。 需着重注意的是,SOA并不是新生事物??大型IT组织成功构建和部署SOA应用已有多年的历史??这要比现有的XML和Web服务长很多。IBM CICS和BEA TUXEDO就是过去被用于构建SOA应用的两种技术范例。 重点说明的是SOA并不是一种现成的技术,而是一种架构和组织IT基础结构及业务功能的方法。SOA是一种在计算环境中设计、开发、部署和管理离散逻辑单元(服务)的模型。这一定义阐明了SOA的范围。 SOA要求开发人员将应用设计为服务的集合。SOA要求开发人员跳出应用本身进行思考,考虑现有服务的重用,或思索他们的服务如何能够被其他项目重用。“单独的”、“独立的”、“封装完善的”服务所具有的一个关键的好处是,可以采用多种不同方法将它们组合成较大型的服务,由此来实现重用。 但是,SOA并不仅仅是一种开发方法??它还具有管理上的优点。例如,现在管理员可直接管理开发人员所构建的相同服务,这远胜于以往管理单个应用的方式。通过分析服务间的交互,SOA可以帮助企业了解何时以及为什么业务逻辑被切实执行了,这使管理员或分析师能够有针对性的优化业务流程。 SOA的基本特征 SOA的实施具有几个鲜明的基本特征。实施SOA的关键目标是实现企业IT资产的最大化重用。要实现这一目标,就要在实施SOA的过程中牢记以下特征: 1 可从企业外部访问 通常被称为业务伙伴的外部用户也能像企业内部用户一样访问相同的服务。业务伙伴采用先进的B2B协议(ebXML或RosettaNet)相互合作。当业务伙伴基于业务目的交换业务信息时,他们就参与了一次会话。会话是业务伙伴间一系列的一条或多条业务信息的交换。会话类型(会话复杂或简单、长或短等)取决于业务目的。 除了B2B协议外,外部用户还可以访问以Web服务方式提供的企业服务。 2 随时可用 当有服务使用者请求服务时,SOA要求必须有服务提供者能够响应。大多数SOA都能够为门户应用之类的同步应用和B2B之类的异步应用提供服务。同步应用对于其所使用的服务具有很强的依赖性。 许多同步应用通常部署在前台,其最终用户很容易受到服务提供者短缺的影响。很多情况下,同步应用利用分布式服务提供者,这样可以响应更多的用户请求。但是,随着提供特定服务功能的服务器数量的增长,出现短缺的可能性也呈指数级上升。 相比之下,异步应用要更为稳健,因为其采用队列请求设计,因此可以容许出现服务提供者短缺或迟滞的情况。异步应用大多数情况下部署在后台,用户通常不会觉察到短暂的短缺。大部分情况下异步应用能够稳健应对短时间短缺,但是长时间短缺则会引发严重问题。在服务短缺解决、队列引擎将罕见的大量工作推到共享的应用资源中时,可能会出现队列溢出甚至服务死锁。 服务使用者要求提供同步服务时,通常是基于其自身理解或使用习惯。在多数情况下,采用异步模型可以达到同样的效果,但更能够体现SOA的最佳特性。 当然,并不是所有情况下都应当采用异步设计模式。但大多数情况下,异步消息可以确保系统在不同负荷下的伸缩性,在接口响应时间不是很短时尤其如此。 3 粗粒度服务接口 粗粒度服务提供一项特定的业务功能,而细粒度服务代表了技术组件方法。举个例说明最为清楚??向计费系统中添加一个客户是典型的粗粒度服务,而你可以使用几个细粒度服务实现同一功能,如:将客户名加入到计费系统中,添加详细的客户联系方式、添加计费信息等等。 采用粗粒度服务接口的优点在于使用者和服务层之间不必再进行多次的往复,一次往复就足够。Internet环境中有保障的TCP/IP会话已不再占据主导、建立连接的成本也过高,因此在该环境中进行应用开发时粗粒度服务接口的优点更为明显。 除去基本的往复效率,事务稳定性问题也很重要。在一个单独事务中包含的多段细粒度请求可能使事务处理时间过长、导致后台服务超时,从而中止。与此相反,从事务的角度来看,向后台服务请求大块数据可能是获取反馈的唯一途径。 4 分级 一个关于粗粒度服务的争论是此类服务比细粒度服务的重用性差,因为粗粒度服务倾向于解决专门的业务问题,因此通用性差、重用性设计困难。解决该争论的方法之一就是允许采用不同的粗粒度等级来创建服务。这种服务分级包含了粒度较细、重用性较高的服务,也包含粒度较粗、重用性较差的服务。 在服务分级方面,须注意服务层的公开服务通常由后台系统(BES's)或SOA平台中现有的本地服务组成。因此允许在服务层创建私有服务是非常重要的。正确的文档、配置管理和私有服务的重用对于IT部门在SOA服务层快速开发新的公开服务的能力具有重要影响。 5 松散耦合 SOA具有“松散耦合”组件服务,这一点区别于大多数其他的组件架构。该方法旨在将服务使用者和服务提供者在服务实现和客户如何使用服务方面隔离开来。 服务提供者和服务使用者间松散耦合背后的关键点是服务接口作为与服务实现分离的实体而存在。这是服务实现能够在完全不影响服务使用者的情况下进行修改。 大多数松散耦合方法都依靠基于服务接口的消息。基于消息的接口能够兼容多种传输方式(如HTTP、JMS、TCP/IP、MOM等)。基于消息的接口可以采用同步和异步协议实现,Web服务对于SOA服务接口来讲是一个重要的标准。 当使用者调用一个Web服务时,被调用的对象可以是CICS事务、DCOM或CORBA对象、J2EE EJB或TUXEDO服务等,但这与服务使用者无关。底层实现并不重要。 消息类Web服务通常是松散耦合和文档驱动的,这要优于与服务特定接口的连接。当客户调用消息类Web服务时,客户通常会发送的是一个完整的文档(如采购订单),而非一组离散的参数。Web服务接收整个文档、进行处理、而后可能或者不会返回结果信息。由于客户和Web服务间不存在紧密耦合请求响应,消息类Web服务在客户和服务器间提供了更为松散的耦合。 6 可重用的服务及服务接口设计管理 如果完全按照可重用的原则设计服务,SOA将可以使应用变得更为灵活。可重用服务采用通用格式提供重要的业务功能,为开发人员节约了大量时间。设计可重用服务是与数据库设计或通用数据建模类似的最有价值的工作。由于服务设计是成功的关键因此,因此SOA实施者应当寻找一种适当的方法进行服务设计过程管理。 服务设计管理根本上讲是服务设计问题,服务设计需要在两点间折衷??走捷径的项目战术与企业构建可重用通用服务的长期目标。 超越项目短期目标进行服务接口的开发和评估是迈向精确定义服务接口的重要一步,同时还需要为接口文档、服务实现文档及所有重要的非功能性特征设立标准。 在大型组织中实现重用的一个先决条件是建立通用(设计阶段)服务库和开发流程,以保证重用的正确性和通用性。此外,对记述服务设计和开发的服务文档进行评估也是成功利用服务库的关键。 简言之,不按规则编写服务将无法保证可提供重用性的SOA的成功实施。在执行规则的过程中会产生财务费用,需要在制定SOA实施计划时加以考虑。 7 标准化的接口 近年来出现的两个重要标准XML和Web服务增加了全新的重要功能,将SOA推向更高的层面,并大大提升了SOA的价值。尽管以往的SOA产品都是专有的、并且要求IT部门在其特定环境中开发所有应用,但XML和Web服务标准化的开放性使企业能够在所部署的所有技术和应用中采用SOA。这具有巨大的意义! Web服务使应用功能得以通过标准化接口(WSDL)提供,并可基于标准化传输方式(HTTP和JMS)、采用标准化协议(SOAP)进行调用。例如,开发人员可以采用最适于门户开发的工具轻松创建一个新的门户应用,并可以重用ERP系统和定制化J2EE应用中的现有服务,而完全无须了解这些应用的内部工作原理。采用XML,门户开发人员无须了解特定的数据表示格式,便能够在这些应用间轻松地交换数据。 你也可以不采用Web服务或XML来创建SOA应用,但是这两种标准的重要性日益增加、应用日趋普遍。尽管目前只有几种服务使用者支持该标准,但未来大多数的服务使用者都会将其作为企业的服务访问方法。 8 支持各种消息模式 SOA中可能存在以下消息模式。在一个SOA实现中,常会出现混合采用不同消息模式的服务。 q 无状态的消息。使用者向提供者发送的每条消息都必须包含提供者处理该消息所需的全部信息。这一限定使服务提供者无须存储使用者的状态信息,从而更易扩展。 q 有状态的消息。使用者与提供者共享使用者的特定环境信息,此信息包含在提供者和使用者交换的消息中。这一限定使提供者与使用者间的通信更加灵活,但由于服务提供者必须存储每个使用者的共享环境信息,因此其整体可扩展性明显减弱。该限定增强了服务提供者和使用者的耦合关系,提高了交换服务提供者的服务难度。 q 等幂消息。向软件代理发送多次重复消息的效果和发送单条消息相同。这一限定使提供者和消费者能够在出现故障时简单的复制消息,从而改进服务可靠性。 9 精确定义的服务接口 服务是由提供者和使用者间的契约定义的。契约规定了服务使用方法及使用者期望的最终结果。此外,还可以在其中规定服务质量。此处需要注意的关键点是,服务契约必须进行精确定义。 META将SOA定义为:“一种以通用为目的、可扩展、具有联合协作性的架构,所有流程都被定义为服务,服务通过基于类封装的服务接口委托给服务提供者,服务接口根据可扩展标识符、格式和协议单独描述。”该定义的最后部分表明在服务接口和其实现之间有明确的分界。 SOA的优点 了解了SOA的定义和基本特征,最后我们再来看看SOA潜在的优点: 编码灵活性 可基于模块化的低层服务、采用不同组合方式创建高层服务,从而实现重用,这些都体现了编码的灵活性。此外,由于服务使用者不直接访问服务提供者,这种服务实现方式本身也可以灵活使用。 明确开发人员角色 例如,熟悉BES的开发人员可以集中精力在重用访问层,协调层开发人员则无须特别了解BES的实现,而将精力放在解决高价值的业务问题上。 支持多种客户类型 借助精确定义的服务接口和对XML、Web服务标准的支持,可以支持多种客户类型,包括PDA、手机等新型访问渠道。 更易维护 服务提供者和服务使用者的松散耦合关系及对开放标准的采用确保了该特性的实现。 更好的伸缩性 依靠服务设计、开发和部署所采用的架构模型实现伸缩性。服务提供者可以彼此独立调整,以满足服务需求。 更高的可用性 该特性在服务提供者和服务使用者的松散耦合关系上得以体现。使用者无须了解提供者的实现细节,这样服务提供者就可以在WebLogic集群环境中灵活部署,使用者可以被转接到可用的例程上。 SOA可以看作是B/S模型、XML/Web Service技术之后的自然延伸。SOA将能够帮助我们站在一个新的高度理解企业级架构中的各种组件的开发、部署形式,它将帮助企业系统架构者以更迅速、更可靠、更具重用性架构整个业务系统。较之以往,以SOA架构的系统能够更加从容地面对业务的急剧变化。 HSQL 学习笔记1. hsql 学习 1.1. 学习目的 本文档是针对hSQL 数据库方面的基础学习,为了使项目组成员能够达到使用hSQL 数据库的目的。 1.2. 培训对象 开发人员 1.3. 常用词及符号说明 常用词: hsql:一种免费的跨平台的数据库系统 E:\hsqldb:表示是在dos 命令窗口下面 1.4. 参考信息 doc\guide\guide.pdf 2. HSQL 2.1. HSQL 运行工具 java -cp ../lib/hsqldb.jar org.hsqldb.util.DatabaseManager 注意hsqldb.jar 文件的文件路径,最好能放到classpath 里面,或者放到当前路径下. java -cp hsqldb.jar org.hsqldb.util.DatabaseManager 2.2. 运行数据库 启动方式: Server Modes and In-Process Mode (also called Standalone Mode). 一个test 数据库会包含如下文件: • test.properties • test.script • test.log • test.data • test.backup test.properties 文件包含关于数据库的一般设置. test.script 文件包含表和其它数据库,插入没有缓存表的数据. test.log 文件包含当前数据库的变更. test.data 文件包含缓存表的数据 test.backup 文件是最近持久化状态的表的数据文件的压缩备份文件 所有以上这个文件都是必要的,不能被删除.如果数据库没有缓存表,test.data 和test.backup 文件将不会存在.另外,除了以上文件HSQLDB 数据库可以链接到任何文本文件,比如cvs 文件. 当操作test 数据库的时候, test.log 用于保存数据的变更. 当正常SHUTDOWN,这个文件将被删除. 否则(不是正常shutdown),这个文件将用于再次启动的时候,重做这些变更.test.lck 文件也用于记录打开的数据库的事实, 正常SHUTDOWN,文件也被删除.在一些情况下,test.data.old 文件会被创建,并删除以前的. 2.3. Server Mode java -cp ../lib/hsqldb.jar org.hsqldb.Server -database.0 file:mydb -dbname.0 xdb 命令行方式: 启动数据,数据库文件mydb,数据库名称xdb 也可以在 server.properties 文件中定义启动的数据库,最多10个 例如: server.properties: server.database.0=file:E:/hsqldb/data/mydb server.dbname.0=xdb server.database.1=file:E:/hsqldb/data/testdb server.dbname.1=testdb server.database.2=mem:adatabase server.dbname.2=quickdb 启动命令: java -cp ../lib/hsqldb.jar org.hsqldb.Server 运行结果如下 java 测试程序: package test; import junit.framework.TestCase; import java.sql.Connection; import java.sql.DriverManager; import java.sql.ResultSet; import java.sql.SQLException; import java.sql.Statement; public class TestConnect extends TestCase { Connection connection; protected void setUp() { try { Class.forName("org.hsqldb.jdbcDriver" ); connection = DriverManager.getConnection("jdbc:hsqldb:hsql://localhost/xdb","sa",""); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } } public void testselect() { Statement stmt=null; ResultSet rs=null; try { stmt = connection.createStatement(); String sql ="select * from test"; rs=stmt.executeQuery( sql); while(rs.next() ) { System.out.println("id="+rs.getString("id")); System.out.println("name="+rs.getString("name")); } } catch (SQLException e) { // TODO Auto-generated catch block e.printStackTrace(); } finally { try { rs.close() ; stmt.close(); } catch (SQLException e) { // TODO Auto-generated catch block e.printStackTrace(); } } } protected void tearDown() { try { connection.close(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } } } 以上在eclipse 中测试通过. 2.4. In-Process (Standalone) Mode 不需要启动server connection = DriverManager.getConnection("jdbc:hsqldb:file:E:/hsqldb/data/mydb","sa",""); 这样就可以连接数据库。 只能在一个jvm 中使用,不能在多个jvm 中使用。 这种模式是在相同的jvm 下作为你的应用程序的一部分,运行数据库引擎。对大多数应用程序,这种模式运行会相当快,作为数据,不需要转换和网络传输。 主要的缺点就是不可能从外面的应用程序访问到默认数据库,因此当你的应用运行时候,你不能通过别的工具检查数据库内容。在1.8.0 版本中,你可以在相同jvm 中的线程中运行数据库初始化,并提供外面访问你的进程内数据库。 推荐在开发应用中使用这种方式。 连接串: Windows: DriverManager.getConnection("jdbc:hsqldb:file:E:/hsqldb/data/mydb","sa",""); Unix: DriverManager.getConnection("jdbc:hsqldb:file:/opt/db/testdb","sa",""); 2.5. Memory-Only Databases 当随即访问内存,数据库不固定时,可以采用内存的方式运行数据库,由于没有数据写到硬盘上,这种方式使用在应用数据和applets 和特殊应用的内部进程中使用,URL: Connection c = DriverManager.getConnection("jdbc:hsqldb:mem:aname", "sa", ""); 2.6. Using Multiple Databases in One JVM 2.7. Different Types of Tables HSQLDB 支持 TEMP 表和三种类型的持久表(MEMORY 表, CACHED 表,TEXT表) 当使用 CREATE TABLE 命令时,Memory 表时默认类型,它们的数据整体保存在内存当中,但是任何改变它们的结构或者内容,它们会被写到<dbname>.script 文件中。这个脚本文件在数据库下一次打开的时候被对出,内存表重新被创建内容,根temp 表不同,内存表时持久化的。 CACHED 表通过CREATE CACHED TABLE 命令建立. 只有部分的它们的数据或者索引被保存在内存中,允许大表占用几百兆的内存空间。例外一个优点,在数据库引擎中,启动大量数据的缓存表需要花费少量的时间,缺点是减慢了运行和使用Hsqldb 的速度。表相对小的时候,不要使用cache 表,在小表中使用内存数据库。 从版本 1.7.0 以后,支持text 表,使用 CSV (Comma Separated Value) 或者其它分隔符文本文件作为它们的数据源。你可以特殊指定一个存在的CSV 文件,例如从其它的数据或者程序中导出文件,作为TXT 表的数据源。 同时,你可以指定一个空文件,通过数据库引擎填充数据。TEXT 表将比cache 表更加效率高。Text 表可以指向不同的数据文件。 * memory-only databases 数据库只支持memory 表和cache 表,不支持text 表。 2.8. 约束和索引 HSQLDB 支持 PRIMARY KEY, NOT NULL, UNIQUE, CHECK and FOREIGN KEY 约束. 3. sql 命令 3.1. sql 支持 select top 1 * from test; select limit 0 2 * from test; DROP TABLE test IF EXISTS; 3.2. Constraints and Indexes 主健约束:PRIMARY KEY 唯一约束: 唯一索引: 外健: CREATE TABLE child(c1 INTEGER, c2 VARCHAR, FOREIGN KEY (c1, c2) REFERENCES parent(p1, p2)); 3.3. 索引和查询速度 索引提高查询速度,比提高排序速度。 主健和唯一所列自动创建索引,否则需要自己创建CREATE INDEX command。 索引: 唯一索引和非唯一索引 多列的索引,如果只是使用后面的,不使用第一个,将不会条查询速度。 (TB is a very large table with only a few rows where TB.COL3 = 4) SELECT * FROM TA JOIN TB ON TA.COL1 = TB.COL2 AND TB.COL3 = 4; SELECT * FROM TB JOIN TA ON TA.COL1 = TB.COL2 AND TB.COL3 = 4;(faster) 原因是 TB.COL3 可以被快速的估计,如果TB 表放到前面(index on TB.COL3): 一般规则是把缩小条件的列的表放在前面 3.4. 使用where 还是join 使用 WHERE 条件链接表可能会降低运行速度. 下面的例子将会比较慢,即使使用了索引: SELECT ... FROM TA, TB, TC WHERE TC.COL3 = TA.COL1 AND TC.COL3=TB.COL2 AND TC.COL4 = 1 这个查询隐含TA.COL1 = TB.COL2 ,但是没有直接设定这个条件.如果 TA 和 TB 每个表都包含100 条记录,10000 组合将和 TC 关联,用于TC这个列的条件,尽管有索引在这个列上.使用JOIN 关键字, 在组合TC 之前,TA.COL1 = TB.COL2 条件直接并缩小组合 TA 和 TB 的行数, 在运行大数据量的表的结果是,将会很快: SELECT ... FROM TA JOIN TB ON TA.COL1 = TB.COL2 JOIN TC ON TB.COL2 = TC.COL3 WHERE TC.COL4 = 1 这个查询可以提高一大步,如果改变表的顺序, 所以 TC.COL1 = 1 将最先使用,这样更小的集合将组合在一起: SELECT ... FROM TC JOIN TB ON TC.COL3 = TB.COL2 JOIN TA ON TC.COL3 = TA.COL1 WHERE TC.COL4 = 1 以上例子,数据引擎自动应用于TC.COL4 = 1 组合小的集合于其它表关联. Indexes TC.COL4, TB.COL2 TA.COL1 都将使用索引,提高查询速度. 3.5. Subqueries and Joins 使用join 和调整表的顺序提高效率. 例如:, 第二个查询的速度将更快一些(TA.COL1 和TB.COL3都有索引): Example 2.2. Query comparison SELECT ... FROM TA WHERE TA.COL1 = (SELECT MAX(TB.COL2) FROM TB WHERE TB.COL3 = 4) SELECT ... FROM (SELECT MAX(TB.COL2) C1 FROM TB WHERE TB.COL3 = 4) T2 JOIN TA ON TA.COL1 = T2.C1 第二个查询将 MAX(TB.COL2) 与一个单记录表相关联. 并使用TA.COL1索引,这将变得非常快. 第一个查询是将 TA 表中的每一条记录不断地与MAX(TB.COL2)匹配. 3.6. 数据类型 TINYINT, SMALLINT, INTEGER, BIGINT, NUMERIC and DECIMAL (without a decimal point) are supported integral types and map to byte, short, int, long and BigDecimal in Java. Integral Types: TINYINT, SMALLINT, INTEGER, BIGINT, NUMERIC and DECIMAL Other Numeric Types: REAL, FLOAT or DOUBLE Bit and Boolean Types: BOOLEAN: UNDEFINED,TRUE,FALSE NULL values are treated as undefined. Storage and Handling of Java Objects Sequences and Identity Identity Auto-Increment Columns: The next IDENTITY value to be used can be set with the ALTER TABLE ALTER COLUMN <column name> RESTART WITH <new value>; Sequences: SELECT NEXT VALUE FOR mysequence, col1, col2 FROM mytable WHERE ... 3.7. 事务问题: SET PROPERTY "sql.tx_no_multi_rewrite" TRUE 4. Connections 通用驱动jdbc:hsqldb: 下列协议标识(mem: file: res: hsql: http: hsqls: https:) Table 4.1. Hsqldb URL Components Driver and Protocol Host and Port Database jdbc:hsqldb:mem: not available accounts jdbc:hsqldb:mem:. jdbc:hsqldb:file: not available mydb /opt/db/accounts C:/data/mydb 数据库路径. jdbc:hsqldb:res: not available /adirectory/dbname jars files are accessed in Java programs. The /adirectory above stands for a directory in one of the jars. jdbc:hsqldb:hsql: jdbc:hsqldb:hsqls: jdbc:hsqldb:http: jdbc:hsqldb:https: //localhost //192.0.0.10:9500 //dbserver.somedomain.com /an_alias /enrollments /quickdb 别名在server.properties or webserver.properties文件中指定 database.0=file:/opt/db/accounts dbname.0=an_alias database.1=file:/opt/db/mydb dbname.1=enrollments database.2=mem:adatabase dbname.2=quickdb In the example below, the database files lists.* in the /home/dbmaster/ directory are associated with the empty alias: database.3=/home/dbmaster/lists dbname.3= 4.1. Connection properties Connection properties are specified either by establishing the connection via the: DriverManager.getConnection (String url, Properties info); method call, or the property can be appended to the full Connection URL. Table 4.2. Connection Properties get_column_name true column name in ResultSet This property is used for compatibility with other JDBC driver implementations. When true (the default), ResultSet.getColumnName(int c) returns the underlying column name When false, the above method returns the same value as ResultSet.getColumnLabel(int column) Example below: jdbc:hsqldb:hsql://localhost/enrollments;get_column_name=false When a ResultSet is used inside a user-defined stored procedure, the default, true, is always used for this property. ifexists false connect only if database already exists Has an effect only with mem: and file: database. When true, will not create a new database if one does not already exist for the URL. When false (the default), a new mem: or file: database will be created if it does not exist. Setting the property to true is useful when troubleshooting as no database is created if the URL is malformed. Example below: jdbc:hsqldb:file:enrollments;ifexists=true shutdown false shut down the database when the last connection is closed This mimics the behaviour of 1.7.1 and older versions. When the last connection to a database is closed, the database is automatically shut down. The property takes effect only when the first connection is made to the database. This means the connection that opens the database. It has no effect if used with subsequent, simultaneous connections. This command has two uses. One is for test suites, where connections to the database are made from one JVM context, immediately followed by another context. The other use is for applications where it is not easy to configure the environment to shutdown the database. Examples reported by users include web application servers, where the closing of the last connection conisides with the web app being shut down. 4.2. Properties Files 大小写敏感 (e.g. server.silent=FALSE will have no effect, but server.silent=false will work). 属性文件和设定存储如下 : Table 4.3. Hsqldb Server Properties Files File Name Location Function server.properties the directory where the command to run the Server class is issued settings for running HSQLDB as a database server communicating with the HSQL protocol webserver.properties the directory where the command to run the WebServer class is issued settings for running HSQLDB as a database server communicating with the HTTP protocol <dbname>.properties the directory where all the files for a database are located settings for each particular database Properties files for running the servers are not created automatically. You should create your own files that contain server.property=value pairs for each property. 4.2.1. Server and Web Server Properties server.properties and webserver.properties 文件支持如下设定: Table 4.4. Property File Properties Value Default Description server.database.0 test the path and file name of the first database file to use server.dbname.0 "" lowercase server alias for the first database file server.urlid.0 NONE SqlTool urlid used by UNIX init script. (This property is not used if your are running Server/Webserver on a platform other than UNIX, or of you are not using our UNIX init script). server.silent true no extensive messages displayed on console server.trace false JDBC trace messages displayed on console In 1.8.0, 每个服务器支持同时启动10个不同的数据库. The server.database.0 property defines the filename / path whereas the server.dbname.0 defines the lowercase alias used by clients to connect to that database. The digit 0 is incremented for the second database and so on. Values for the server.database.{0-9} property can use the mem:, file: or res: prefixes and properties as discussed above under CONNECTIONS. For example, database.0=mem:temp;sql.enforce_strict_size=true; Values specific to server.properties are: Table 4.5. Server Property File Properties Value Default Description server.port 9001 TCP/IP port used for talking to clients. All databases are served on the same port. server.no_system_exit true no System.exit() call when the database is closed Values specific to webserver.properties are: Table 4.6. WebServer Property File Properties Value Default Description server.port 80 TCP/IP port used for talking to clients server.default_page index.html the default web page for server server.root ./ the location of served pages .<extension> ? multiple entries such as .html=text/html define the mime types of the static files served by the web server. See the source for WebServer.java for a list. All the above values can be specified on the command line to start the server by omitting the server. prefix. 5. SqlTool Mem 数据库: E:\hsqldb>java -jar ./lib/hsqldb.jar mem Hsql Server: (前提是xdb server 已经启动): (java -cp ../lib/hsqldb.jar org.hsqldb.Server -database.0 file:mydb -dbname.0 xdb) java -jar ./hsqldb.jar xdb 执行sql 语句: 1) Mydb.sql : CREATE MEMORY TABLE TEST(ID INTEGER,NAME VARCHAR(20)); INSERT INTO TEST VALUES(1,'aaa'); INSERT INTO TEST VALUES(2,'bbb'); E:\hsqldb>java -jar ./lib/hsqldb.jar mem mydb.sql 1 row updated 1 row updated 2) testuser.sql: CREATE MEMORY TABLE userTEST(ID INTEGER,NAME VARCHAR(20)); INSERT INTO userTEST VALUES(1,'aaa'); INSERT INTO userTEST VALUES(2,'bbb'); commit; //这样才能提交到数据库 E:\hsqldb>java -jar ./hsqldb.jar xdb testuser.sql > file.txt 2>&1 输出结果到file.txt 文件中. 连接oracle: E:\hsqldb>java -classpath ./classes12.zip;./hsqldb.jar org.hsqldb.util.SqlTool --driver oracle.jdbc.driver.OracleDriver orcl sqltool.rc 文件: urlid orcl url jdbc:oracle:thin:@localhost:1521:livedoor username scott password tiger driver oracle.jdbc.OracleDriver 以上driver 在一处写出即可,也可以连接别的数据库 连接mysql E:\hsqldb>java -classpath ./lib/mysql-connector-java-3.1.10-bin.jar;./hsqldb.jar org.hsqldb.util.SqlTool mysqltest .rc 文件内容: urlid mysqltest url jdbc:mysql://localhost:3306/test username root password root driver com.mysql.jdbc.Driver 6. sql 语法 6.1.1. ALTER INDEX[1] ALTER INDEX <indexname> RENAME TO <newname>; 6.1.2. ALTER SEQUENCE[1] ALTER SEQUENCE <sequencename> RESTART WITH <value>; 6.1.3. ALTER SCHEMA[1] ALTER SCHEMA <schemaname> RENAME TO <newname>; 6.1.4. ALTER TABLE[1] ALTER TABLE <tablename> ADD [COLUMN] <columnname> Datatype [(columnSize[,precision])] [{DEFAULT <defaultValue> | GENERATED BY DEFAULT AS IDENTITY (START WITH <n>[, INCREMENT BY <m>])}] | [[NOT] NULL] [IDENTITY] [PRIMARY KEY] [BEFORE <existingcolumn>]; ALTER TABLE <tablename> DROP [COLUMN] <columnname>; ALTER TABLE <tablename> ALTER COLUMN <columnname> RENAME TO <newname> ALTER TABLE <tablename> ALTER COLUMN <columnname> SET DEFAULT <defaultvalue>}; ALTER TABLE <tablename> ALTER COLUMN <columnname> SET [NOT] NULL ALTER TABLE <tablename> ALTER COLUMN <columnDefinition>; ALTER TABLE <tablename> ALTER COLUMN <columnname> RESTART WITH <new sequence value> ALTER TABLE <tablename> ADD [CONSTRAINT <constraintname>] CHECK (<search condition>); ALTER TABLE <tablename> ADD [CONSTRAINT <constraintname>] UNIQUE (<column list>); ALTER TABLE <tablename> ADD [CONSTRAINT <constraintname>] PRIMARY KEY (<column list>); ALTER TABLE <tablename> ADD [CONSTRAINT <constraintname>] FOREIGN KEY (<column list>) REFERENCES <exptablename> (<column list>) [ON {DELETE | UPDATE} {CASCADE | SET DEFAULT | SET NULL}]; ALTER TABLE <tablename> DROP CONSTRAINT <constraintname>; ALTER TABLE <tablename> RENAME TO <newname>; 6.1.5. ALTER USER[1] ALTER USER <username> SET PASSWORD <password>; ALTER USER <username> SET INITIAL SCHEMA <schemaname>; 6.1.6. CALL CALL Expression; See also: Stored Procedures / Functions, SQL Expression. 6.1.7. CHECKPOINT CHECKPOINT [DEFRAG[1]]; See also: SHUTDOWN, SET LOGSIZE. 6.1.8. COMMIT COMMIT [WORK]; See also: ROLLBACK, SET AUTOCOMMIT, SET LOGSIZE. 6.1.9. CONNECT CONNECT USER <username> PASSWORD <password>; See also: GRANT, REVOKE. 6.1.10. CREATE ALIAS CREATE ALIAS <function> FOR <javaFunction>; See also: CALL, Stored Procedures / Functions. 6.1.11. CREATE INDEX CREATE [UNIQUE] INDEX <index> ON <table> (<column> [DESC] [, ...]) [DESC]; 6.1.12. CREATE ROLE[1] CREATE ROLE <rolename>; 6.1.13. CREATE SCHEMA[1] CREATE SCHEMA <schemaname> AUTHORIZATION <grantee> [<createStatement> [<grantStatement>] [...]; CREATE SCHEMA ACCOUNTS AUTHORIZATION DBA CREATE TABLE AB(A INTEGER, ...) CREATE TABLE CD(C CHAHR, ...) CREATE VIEW VI AS SELECT ... GRANT SELECT TO PUBLIC ON AB GRANT SELECT TO JOE ON CD; 6.1.14. CREATE SEQUENCE[1] CREATE SEQUENCE <sequencename> [AS {INTEGER | BIGINT}] [START WITH <startvalue>] [INCREMENT BY <incrementvalue>]; SELECT [...,] NEXT VALUE FOR <sequencename> [, ...] FROM <tablename>; 6.1.15. CREATE TABLE CREATE [MEMORY | CACHED | [GLOBAL] TEMPORARY | TEMP [1] | TEXT[1]] TABLE <name> ( <columnDefinition> [, ...] [, <constraintDefinition>...] ) [ON COMMIT {DELETE | PRESERVE} ROWS]; 6.1.16. CREATE TRIGGER[1] CREATE TRIGGER <name> {BEFORE | AFTER} {INSERT | UPDATE | DELETE} ON <table> [FOR EACH ROW] [QUEUE n] [NOWAIT] CALL <TriggerClass>; 6.1.17. CREATE USER CREATE USER <username> PASSWORD <password> [ADMIN]; 6.1.18. CREATE VIEW[1] CREATE VIEW <viewname>[(<viewcolumn>,..) AS SELECT ... FROM ... [WHERE Expression] [ORDER BY orderExpression [, ...]] [LIMIT <limit> [OFFSET <offset>]]; CREATE VIEW mealsjv AS SELECT m.mid mid, m.name name, t.mealtype mt, a.aid aid, a.gname + ' ' + a.sname author, m.description description, m.asof asof FROM meals m, mealtypes t, authors a WHERE m.mealtype = t.mealtype AND m.aid = a.aid; CREATE VIEW mealswebv AS SELECT name, author FROM mealsjv; CREATE VIEW aview (new_name, new_author) AS SELECT name, author FROM mealsjv 6.1.19. DELETE DELETE FROM table [WHERE Expression]; 6.1.20. DISCONNECT DISCONNECT; 6.1.21. DROP INDEX DROP INDEX index [IF EXISTS]; 6.1.22. DROP ROLE[1] DROP ROLE <rolename>; 6.1.23. DROP SEQUENCE[1] DROP SEQUENCE <sequencename> [IF EXISTS] [RESTRICT | CASCADE]; 6.1.24. DROP SCHEMA[1] DROP SCHEMA <schemaname> [RESTRICT | CASCADE]; 6.1.25. DROP TABLE DROP TABLE <table> [IF EXISTS] [RESTRICT | CASCADE]; 6.1.26. DROP TRIGGER DROP TRIGGER <trigger>; 6.1.27. DROP USER DROP USER <username>; 6.1.28. DROP VIEW[1] DROP VIEW <viewname> [IF EXISTS] [RESTRICT | CASCADE]; 6.1.29. EXPLAIN PLAN EXPLAIN PLAN FOR { SELECT ... | DELETE ... | INSERT ... | UPDATE ..}; 6.1.30. GRANT GRANT { SELECT | DELETE | INSERT | UPDATE | ALL } [,...] ON { table | CLASS "package.class" } TO <grantee>; GRANT <rolename> [,...] TO <grantee>[1]; GRANT SELECT ON Test TO GUEST; GRANT ALL ON CLASS "java.lang.Math.abs" TO PUBLIC; 6.1.31. INSERT INSERT INTO table [( column [,...] )] { VALUES(Expression [,...]) | SelectStatement}; 6.1.32. REVOKE REVOKE { SELECT | DELETE | INSERT | UPDATE | ALL } [,...] ON { table | CLASS "package.class" } FROM <grantee>; REVOKE <rolename> [,...] FROM <grantee>[1]; 6.1.33. ROLLBACK ROLLBACK [TO SAVEPOINT <savepoint name>[1] | WORK}]; 6.1.34. SAVEPOINT[1] SAVEPOINT <savepoint name>; 6.1.35. SCRIPT SCRIPT ['file']; 6.1.36. SELECT[1] SELECT [{LIMIT <offset> <limit> | TOP <limit>}[1]][ALL | DISTINCT] { selectExpression | table.* | * } [, ...] [INTO [CACHED | TEMP | TEXT][1] newTable] FROM tableList [WHERE Expression] [GROUP BY Expression [, ...]] [HAVING Expression] [{ UNION [ALL | DISTINCT] | {MINUS [DISTINCT] | EXCEPT [DISTINCT] } | INTERSECT [DISTINCT] } selectStatement] [ORDER BY orderExpression [, ...]] [LIMIT <limit> [OFFSET <offset>]]; tableList table [{CROSS | INNER | LEFT OUTER | RIGHT OUTER} JOIN table ON Expression] [, ...] table { (selectStatement) [AS] label | tableName} selectExpression { Expression | COUNT(*) | { COUNT | MIN | MAX | SUM | AVG | SOME | EVERY | VAR_POP | VAR_SAMP | STDDEV_POP | STDDEV_SAMP } ([ALL | DISTINCT][1]] Expression) } [[AS] label] If CROSS JOIN is specified no ON expression is allowed for the join. orderExpression { columnNr | columnAlias | selectExpression } [ASC | DESC] LIMIT n m LIMIT n m LIMIT m OFFSET n TOP m UNION and other set operations 6.1.37. SET AUTOCOMMIT SET AUTOCOMMIT { TRUE | FALSE }; 6.1.38. SET DATABASE COLLATION[1] SET DATABASE COLLATION <double quoted collation name>; 6.1.39. SET CHECKPOINT DEFRAG[1] SET CHECKPOINT DEFRAG <size>; 6.1.40. SET IGNORECASE SET IGNORECASE { TRUE | FALSE }; 6.1.41. SET INITIAL SCHEMA [1] Users may change their base default schema name with the comand SET INITIAL SCHEMA <schemaname>; 6.1.42. SET LOGSIZE SET LOGSIZE <size>; 6.1.43. SET PASSWORD SET PASSWORD <password>; 6.1.44. SET PROPERTY[1] SET PROPERTY <double quoted name> <value>; 6.1.45. SET REFERENTIAL INTEGRITY SET REFERENTIAL_INTEGRITY { TRUE | FALSE }; 6.1.46. SET SCHEMA[1] SET SCHEMA <schemaname>; 6.1.47. SET SCRIPTFORMAT[1] SET SCRIPTFORMAT {TEXT | BINARY | COMPRESSED}; 6.1.48. SET TABLE INDEX SET TABLE tableName INDEX 'index1rootPos index2rootPos ... '; 6.1.49. SET TABLE READONLY[1] SET TABLE <tablename> READONLY {TRUE | FALSE}; 6.1.50. SET TABLE SOURCE[1] SET TABLE <tablename> SOURCE <file and options> [DESC]; SET TABLE mytable SOURCE "myfile;fs=|;vs=.;lvs=~" Supported Properties quoted = { true | false } default is true. If false, treats double quotes as normal characters all_quoted = { true | false } default is false. If true, adds double quotes around all fields. encoding = <encoding name> character encoding for text and character fields, for example, encoding=UTF-8 ignore_first = { true | false } default is false. If true ignores the first line of the file cache_scale= <numeric value> exponent to calculate rows of the text file in cache. Default is 8, equivalent to nearly 800 rows cache_size_scale = <numeric value>r exponent to calculate average size of each row in cache. Default is 8, equivalent to 256 bytes per row. fs = <unquoted character> field separator vs = <unquoted character> varchar separator lvs = <unquoted character> long varchar separator Special indicators for Hsqldb Text Table separators \semi semicolon \quote quote \space space character \apos apostrophe \n newline - Used as an end anchor (like $ in regular expressions) \r carriage return \t tab \\ backslash \u#### a Unicode character specified in hexadecimal Only an administrator may do this. 6.1.51. SET WRITE DELAY[1] SET WRITE_DELAY {{ TRUE | FALSE } | <seconds> | <milliseconds> MILLIS}; 6.1.52. SHUTDOWN SHUTDOWN [IMMEDIATELY | COMPACT | SCRIPT[1]]; 6.2. Data Types Table 9.1. Data Types. The types on the same line are equivalent. Name Range Java Type INTEGER | INT as Java type int | java.lang.Integer DOUBLE [PRECISION] | FLOAT as Java type double | java.lang.Double VARCHAR as Integer.MAXVALUE java.lang.String VARCHAR_IGNORECASE as Integer.MAXVALUE java.lang.String CHAR | CHARACTER as Integer.MAXVALUE java.lang.String LONGVARCHAR as Integer.MAXVALUE java.lang.String DATE as Java type java.sql.Date TIME as Java type java.sql.Time TIMESTAMP | DATETIME as Java type java.sql.Timestamp DECIMAL No limit java.math.BigDecimal NUMERIC No limit java.math.BigDecimal BOOLEAN | BIT as Java type boolean | java.lang.Boolean TINYINT as Java type byte | java.lang.Byte SMALLINT as Java type short | java.lang.Short BIGINT as Java type long | java.lang.Long REAL as Java type double | java.lang.Double[1] BINARY as Integer.MAXVALUE byte[] VARBINARY as Integer.MAXVALUE byte[] LONGVARBINARY as Integer.MAXVALUE byte[] OTHER | OBJECT as Integer.MAXVALUE java.lang.Object The uppercase names are the data types names defined by the SQL standard or commonly used by RDMS's. The data types in quotes are the Ja 6.2.1. 自动增长: create table user(id IDENTITY,name varchar(20)); sql> create table dept(id int GENERATED BY DEFAULT AS IDENTITY(start with 10,increment by 5) not null PRIMARY KEY,name v archar(20)); sql> insert into dept(name) values('asc'); 1 row updated sql> insert into dept(name) values('security'); 1 row updated sql> select * from dept; ID NAME -- -------- 10 asc 15 security 2 rows 6.3. SQL Comments -- SQL style line comment // Java style line comment /* C style line comment */ 7. Hsqldb Test Utility 拷贝 junit.jar 到/lib 目录下 运行: ant hsqldbtest 生成 hsqldbtest.jar 运行: \hsqldb\testrun\hsqldb>runtest TestSelf Mysql 学习1. Mysql 培训 1.1. 培训目的 本文档是针对MySQL 数据库方面的基础培训,为了使项目组成员能够达到使用MySQL 数据库的目的。 1.2. 培训对象 开发人员 1.3. 常用词及符号说明 常用词: Mysql:一种免费的跨平台的数据库系统 E:\mysql:表示是在dos 命令窗口下面 mysql> 表示是在mysql 的命令行下 1.4. 参考信息 http://dev.mysql.com/doc/refman/5.0/en/index.html 2. MYSQL 2.1. 连接MYSQL 格式: mysql -h主机地址 -u用户名 -p用户密码 连接远程机器: E:\mysql>mysql -h10.4.3.188 -uptsdb -p 等价写法 E:\mysql>mysql --host=10.4.3.188 --user=ptsdb --password 连接本地机器: E:\mysql>mysql -uroot -p 等价写法 E:\mysql>mysql --user=root -password (注:u与root可以不用加空格,其它也一样) 注意事项:环境变量path 里面要设定mysql的bin的路径: C:\Program Files\MySQL\MySQL Server 5.0\bin 2.2. 修改密码 方法一:使用mysqladmin 格式:mysqladmin -u用户名 -p旧密码 password 新密码 例1:E:\mysql>mysqladmin -uroot password root 注:因为开始时root没有密码,所以-p旧密码一项就可以省略了。 例2:再将root的密码改为root123。 E:\mysql>mysqladmin -uroot -proot password root123 方法二:直接更新 user 表 mysql>UPDATE user SET password=PASSWORD("test123") WHERE user='test'; mysql> FLUSH PRIVILEGES; mysql> SET PASSWORD FOR test=PASSWORD('test123'); mysql> FLUSH PRIVILEGES; 方法三:使用 grant 格式:grant 权限 on 数据库.表格| 其他 to 用户@主机 IDENTIFIED BY 口令 例1:给test用户在本地localhost 所有权限(除了GRANT OPTION),口令为 test (相当于修改了test 用户的口令) mysql>grant all on *.* to test@localhost identified by "test"; 等同于 mysql>grant all on *.* to test @localhost identified by PASSWORD " *94BDCEBE19083CE2A1F959FD02F964C7AF4CFC29 "; 例2、增加一个用户test密码为abc,让他可以在任何主机上登录,并对test数据库有查询、插入、修改、删除的权限。首先用以root用户连入MYSQL,然后键入以下命令: mysql>grant select,insert,update,delete on test.* to test@"%" Identified by "abc"; 在mysql.user 表中,有两个test 用户 一个test 用户,在本地有所有的权限 另外的test 用户,在所有主机上有增删改查权限 同样可以取消部分权限(全部) mysql>revoke insert,update,delete on test.* from test@"%" mysql>REVOKE ALL PRIVILEGES, GRANT OPTION FROM test@"%" 然后 mysql> FLUSH PRIVILEGES; Test 用户不再使用用了,也可以删除 mysql>Delete from user where user='test' and host='%' mysql> FLUSH PRIVILEGES; 注意:例2增加的用户是比较危险的,你想如某个人知道test的密码,那么他就可以在internet上的任何一台电脑上登录你的mysql数据库并对你的数据库test为所欲为了(可以通过限定主机) mysql>grant select,insert,update,delete on test.* to test@"IP地址" Identified by "abc"; 2.3. 显示命令 显示数据库列表: mysql>show databases; mysql>show schemas; --mysql 5.0.2 显示表格 mysql>show tables from mydb; 显示表格状态 Mysql>SHOW TABLE STATUS; 显示字符集: mysql> SHOW CHARACTER SET; 显示创建表: mysql> show create table quote; 显示用户权限: mysql> SHOW GRANTS FOR 'test'@'localhost'; mysql>SHOW GRANTS; mysql>SHOW GRANTS FOR CURRENT_USER; mysql>SHOW GRANTS FOR CURRENT_USER(); 显示index: mysql>SHOW INDEX FROM mydb.mytable; 显示表结构: mysql>desc mydb.tablename; mysql>show columns from mydb.tablename; 显示MySQL数据库的版本: mysql>select version(); 显示函数 mysql>Select * from mysql.func; 显示存储过程 mysql>Select * from mysql.proc; 显示存储引擎 mysql> SHOW ENGINES; 显示变量: mysql>SHOW VARIABLES; 显示状态: Mysql> SHOW STATUS; 显示进程 Mysql>SHOW PROCESSLIST 显示 INNODB 状态 Mysql>SHOW INNODB STATUS 显示连接状态 Mysql>SHOW STATUS LIKE '%CONNECT%'; 显示线程状态 Mysql>SHOW STATUS LIKE '%THREAD%'; 等等.. 2.4. 创建.修改.删除 2.4.1. 创建数据库 CREATE {DATABASE | SCHEMA} [IF NOT EXISTS] db_name [create_specification [, create_specification] ...] create_specification: [DEFAULT] CHARACTER SET charset_name | [DEFAULT] COLLATE collation_name 例如: CREATE DATABASE IF NOT EXISTS ddd --如果不存在,则创建. CHARACTER SET 'ujis' --设定字符集 COLLATE 'ujis_japanese_ci'; 2.4.2. 创建表 CREATE [TEMPORARY] TABLE [IF NOT EXISTS] tbl_name [(create_definition,...)] [table_options] [select_statement] 例子: CREATE TABLE if not exists `Admin_User` ( `id` int(11) NOT NULL auto_increment, --PRIMARY KEY, `livedoorId` varchar(255) NOT NULL default '', `password` varchar(255) NOT NULL default '', `auth` int(11) default '0', PRIMARY KEY (`id`) --设定主健 ) ENGINE=MyISAM DEFAULT CHARSET=ujis ?设定字符集 ENGINE=MyISAM 默认存储引擎 The binary portable storage engine that is the default storage engine used by MySQL 对于每个MyISAM 存储引擎的表,在硬盘上存在3个文件 File Purpose tbl_name.frm Table format (definition) file tbl_name.MYD Data file tbl_name.MYI Index file ENGINE= InnoDB Transaction-safe tables with row locking and foreign keys. ENGINE = BDB Transaction-safe tables with page locking. 还有其他的内存引擎 MEMORY 归档 ARCHIVE 等等 ISAM 不再使用了 2.4.3. 创建索引 CREATE [UNIQUE|FULLTEXT|SPATIAL] INDEX index_name [USING index_type] ON tbl_name (index_col_name,...) index_col_name: col_name [(length)] [ASC | DESC] 将customer 表的name 字段前十个字符做为索引 CREATE INDEX part_of_name ON customer (name(10)); MYSQL 5.0 特性 存储引擎为 MyISAM, InnoDB, or BDB 的表格上,可以在有null值的字段上创建索引 存储引擎为 MyISAM, InnoDB, or BDB 的表格上,可以在BLOB TEXT 上创建索引 只有在MyISAM 类型表格上,可以在CHAR, VARCHAR, and TEXT 字段类型上创建FULLTEXT 索引 Storage Engine Allowable Index Types MyISAM BTREE InnoDB BTREE MEMORY/HEAP HASH, BTREE 可以指定索引类型 Example: CREATE TABLE testtable (id INT) ENGINE = MEMORY; CREATE INDEX id_index USING BTREE ON testtable (id); 2.4.4. 修改表 ALTER [IGNORE] TABLE tbl_name alter_specification [, alter_specification] ... IGNORE 忽略主健重复的错误,如果重复,采用第一条,其余删除 例子:同时多个操作 mysql> ALTER TABLE t2 DROP COLUMN c, DROP COLUMN d; 例子, 重命名 INTEGER 字段,从 a 到 b: mysql> ALTER TABLE t1 CHANGE a b INTEGER; 例子 修改字段类型,仍然需要新旧字段名称,即使字段名称相同: mysql> ALTER TABLE t1 CHANGE b b BIGINT NOT NULL; 也可以使用modify mysql> ALTER TABLE t1 MODIFY b BIGINT NOT NULL; 在mysql 5.0 可以使用FIRST or AFTER 字段来添加add 字段,默认是在最后 modify change 也可以使用 在mysql 5.0 InnoDB 存储引擎支持 ALTER TABLE 删除外健: mysql>ALTER TABLE yourtablename DROP FOREIGN KEY fk_symbol; 例子: 创建表 mysql> CREATE TABLE t1 (a INTEGER,b CHAR(10)); 重命名表 mysql> ALTER TABLE t1 RENAME t2; MODIFY a 字段为 TINYINT NOT NULL , 并且 change 字段 b,从 CHAR(10) 到 CHAR(20) 并改名为c: mysql> ALTER TABLE t2 MODIFY a TINYINT NOT NULL, CHANGE b c CHAR(20); 添加新字段 d: mysql> ALTER TABLE t2 ADD d TIMESTAMP; 在a d 上增加索引: mysql> ALTER TABLE t2 ADD INDEX (d), ADD INDEX (a); 删除字段c: mysql> ALTER TABLE t2 DROP COLUMN c; 添加一个自动增长的字段c ,并且添加c 为主健: mysql> ALTER TABLE t2 ADD c INT UNSIGNED NOT NULL AUTO_INCREMENT, -> ADD PRIMARY KEY (c); 2.4.4.1. 修改外键 语法: ALTER TABLE tbl_name ADD [CONSTRAINT symbol] FOREIGN KEY [id] (index_col_name, ...) REFERENCES tbl_name (index_col_name, ...) [ON DELETE {RESTRICT | CASCADE | SET NULL | NO ACTION}] [ON UPDATE {RESTRICT | CASCADE | SET NULL | NO ACTION}] 例子: create table aa (id1 int not null,name varchar(20),primary key(id1))type=InnoDB; create table b(id2 int not null,lessonname varchar(20),primary key(id2))type=InnoDB; alter table b add FOREIGN KEY id (id2) references aa(id1); 2.4.5. 删除 删除数据库 DROP {DATABASE | SCHEMA} [IF EXISTS] db_name 例子: mysql>drop DATABASE IF EXISTS testdb; 删除表 DROP [TEMPORARY] TABLE [IF EXISTS] tbl_name [, tbl_name] ... [RESTRICT | CASCADE] 例子: mysql>drop TABLE IF EXISTS testTable; 删除索引 DROP INDEX index_name ON tbl_name 例子: mysql>drop index testIndex on testTable; 重命名 RENAME TABLE tbl_name TO new_tbl_name [, tbl_name2 TO new_tbl_name2] ... 例子:RENAME TABLE current_db.tbl_name TO other_db.tbl_name; 2.5. 数据库备份恢复 数据库备份 数据库备份命令: mysqldump --opt --user=用户名 --password=密码 --default_character-set=字符集 -B数据库> 输出的sql文件 例子: E:\mysql>Mysqldump --user=ptsdb --password=ptsdb --default_character-set=ujis --opt pts>dump.sql 参见批处理文件 数据库导入命令: mysql --user=用户名 --password=密码 --default_character-set=字符集 [数据库]<导入的sql 语句 E:\mysql>mysql -uptsdb -pptsdb --default-character-set=ujis<E:\mysql\backups\dbBkup_ddd_2005-11-11_14时40分.sql 例子: 对于InnoDB(没有设定字符集) Following mysqldump import example for InnoDB tables is at least 100x faster than previous examples. 1. mysqldump --opt --user=username --password database > dumbfile.sql 2. Edit the dump file and put these lines at the beginning: SET AUTOCOMMIT = 0; SET FOREIGN_KEY_CHECKS=0; 3. Put these lines at the end: SET FOREIGN_KEY_CHECKS = 1; COMMIT; SET AUTOCOMMIT = 1; 4. mysql --user=username --password database < dumpfile.sql 参数说明: --add-drop-database Add a DROP DATABASE statement before each CREATE DATABASE statement. --add-drop-table Add a DROP TABLE statement before each CREATE TABLE statement. --all-databases, -A Dump all tables in all databases. This is the same as using the --databases option and naming all the databases on the command line. --databases, -B Dump several databases. Normally, mysqldump treats the first name argument on the command line as a database name and following names as table names. With this option, it treats all name arguments as database names. CREATE DATABASE IF NOT EXISTS db_name and USE db_name statements are included in the output before each new database. --host=host_name, -h host_name Dump data from the MySQL server on the given host. The default host is localhost. --opt This option is shorthand; it is the same as specifying --add-drop-table --add-locks --create-options --disable-keys --extended-insert --lock-tables --quick --set-charset. It should give you a fast dump operation and produce a dump file that can be reloaded into a MySQL server quickly. In MySQL 5.0, --opt is on by default, but can be disabled with --skip-opt. To disable only certain of the options enabled by --opt, use their --skip forms; for example, --skip-add-drop-table or --skip-quick. 还有一些其他参数,有兴趣可以学习 2.6. 表数据备份 mysql>use test; mysql> CREATE TABLE imptest(id INT, n VARCHAR(30)); Query OK, 0 rows affected (0.03 sec) 方法一: 导出使用:Mysqldump E:\mysql>mysqldump -uptsdb -pptsdb -where "id>='100'" test imptest E:\mysql>mysqldump -uptsdb -pptsdb test imptest>e:\mysql\imp\imptest2.txt 导入使用 mysql mysql -uptsdb -pptsdb< imptest2.txt 方法二: 导出使用 select into OUTFILE mysql> select * from imptest where id=101 into OUTFILE 'e:\\mysql\\imp\\test3.txt' FIELDS TERMINATED BY ','; 导入使用 LOAD DATA INFILE LOAD DATA [LOW_PRIORITY | CONCURRENT] [LOCAL] INFILE 'file_name.txt' [REPLACE | IGNORE] INTO TABLE tbl_name [FIELDS [TERMINATED BY 'string'] [[OPTIONALLY] ENCLOSED BY 'char'] [ESCAPED BY 'char' ] ] [LINES [STARTING BY 'string'] [TERMINATED BY 'string'] ] [IGNORE number LINES] [(col_name_or_user_var,...)] [SET col_name = expr,...]] 例子: mysql> LOAD DATA INFILE 'e:\\mysql\\imp\\test3.txt' INTO TABLE imptest FIELDS TERMINATED BY ','; 导入使用mysqlimport: E:\mysql>mysqlimport -uptsdb -pptsdb --local test E:\mysql\imp\imp.txt mysqlimport: Error: Table 'test.imp' doesn't exist, when using table: imp E:\mysql>mysqlimport -uptsdb -pptsdb --local test E:\mysql\imp\imptest.txt test.imptest: Records: 2 Deleted: 0 Skipped: 0 Warnings: 0 注意:文件名必须跟表名相同 参数 -d or --delete 新数据导入数据表中之前删除数据数据表中的所有信息 -f or --force 不管是否遇到错误,mysqlimport将强制继续插入数据 -i or --ignore mysqlimport跳过或者忽略那些有相同唯一 -r or -replace 这个选项与-i选项的作用相反;此选项将替代 表中有相同唯一关键字的记录 2.7. 数据管道导入导出 E:\mysql>mysql -h10.5.1.66 -uroot -proot --default-character-set=name frontdb_20060415(databasename) >e:/mysql/test.txt (输出的sql 语句) <e:/mysql/test.txt (输入的要执行的sql 语句) 1:>;create databases newname(在新的server上建立空的数据库) 2:#/usr/local/mysql/bin/mysqldump databasename >*.sql(在旧的服务器上导出数据库) 3:#/usr/local/mysql/bin/mysql databasename < *.sql(在新的服务器上导入*.sql) 注意数据库名要一一对应. 2.8. 各种字段的取值范围 TINYINT 1 byte -128 - 127 TINYINT UNSIGNED 1 byte 0 ? 255 即0-(28-1) SMALLINT 2 bytes -32768 - 32767 即-215至(215-1) SMALLINT UNSIGNED 2 bytes 0 - 65535 即0至(216-1) MEDIUMINT 3 bytes -8388608 - 8388607 即?223至(223-1) MEDIUMINT UNSIGNED 3 bytes 0 - 16777215 即0至(224-1) INT 或 INTEGER 4 bytes -2147483648 - 2147483647 即?231至(231-1) INT UNSIGNED 或 INTEGER UNSIGNED 4 bytes 0 - 4294967295 即0至(232-1) BIGINT 8 bytes -9223372036854775808 - 9223372036854775807 即?263至(263-1) BIGINT UNSIGNED 8 bytes 0 - 18446744073709551615 即0至(264-1) FLOAT 4 bytes -3.402823466E+38 - -1.175494351E-38 0 1.175494351E-38 - 3.402823466E+38 DOUBLE 或 DOUBLE PRECISION 或 REAL 8 bytes -1.7976931348623157E+308 - -2.2250738585072014E-308 0 2.2250738585072014E-308 - 1.7976931348623157E+308 DECIMAL[(M,[D])] 或 NUMERIC(M,D) 不定 由M(整个数字的长度,包括小数点,小数点左边的位数,小数点右边的位数,但不包括负号)和 D(小数点右边的位数)来决定,M缺省为10,D缺省为0 DATE 3 bytes 1000-01-01 - 9999-12-31 DATETIME 8 bytes 1000-01-01 00:00:00 - 9999-12-31 23:59:59 TIMESTAMP 4 bytes 1970-01-01 00:00:00 - 2037-12-31 23:59:59 TIME 3 bytes -838:59:59' to 838:59:59 YEAR[(2|4)] 1 byte 缺省为4位格式,4位格式取值范围为1901 - 2155,0000,2位格式取值范围为70-69(1970-2069) CHAR(M) [BINARY] 或 NCHAR(M) [BINARY] M bytes M的范围为1 - 255,如果没有BINARY项,则不分大小写,NCHAR表示使用缺省的字符集.在数据库 中以空格补足,但在取出来时末尾的空格将被去掉. [NATIONAL] VARCHAR(M) [BINARY] Before 5.0.3 M的范围为0?255 L+1 bytes L<=M 5.0.3 以及以后 M 范围为 0-65535 L+1 bytes L<=M 0<=M<=256 L+2 bytes L<=M 256<M<=65535 在数据库中末尾的空格将自动去掉. TINYBLOB 或 TINYTEXT L+1 bytes 255(2^8-1)个字符 BLOB 或 TEXT L+2 bytes 65535(2^16-1)个字符 MEDIUMBLOB 或 MEDIUMTEXT L+3 bytes 16777215 (2^24-1)个字符 LONGBLOB 或 LONGTEXT L+4 bytes 4294967295 (2^32-1)个字符 ENUM('value1','value2',...) 1 or 2 bytes 可以总共有65535个不同的值 SET('value1','value2',...) 1/2/3/4/8 bytes 最多有64个成员 2.9. 查询 2.9.1. limit LIMIT子句可以用来限制由SELECT语句返回过来的数据数量,它有一个或两个参数,如果给出两个参数, 第一个参数指定返回的第一行在所有数据中的位置,从0开始(注意不是1),第二个参数指定最多返回行 数。例如: select * from table LIMIT 5,10; #返回第6-15行数据 select * from table LIMIT 5; #返回前5行 select * from table LIMIT 0,5; #返回前5行 2.9.2. join 详解 还是先 Create table 吧 create table emp( id int not null primary key, name varchar(10) ); create table emp_dept( dept_id varchar(4) not null, emp_id int not null, emp_name varchar(10), primary key (dept_id,emp_id)); insert into emp() values (1,"Dennis-1"), (2,"Dennis-2"), (3,"Dennis-3"), (4,"Dennis-4"), (5,"Dennis-5"), (6,"Dennis-6"), (7,"Dennis-7"), (8,"Dennis-8"), (9,"Dennis-9"), (10,"Dennis-10"); insert into emp_dept() values ("R&D",1,"Dennis-1"), ("DEv",2,"Dennis-2"), ("R&D",3,"Dennis-3"), ("Test",4,"Dennis-4"), ("Test",5,"Dennis-5"); ("dddd",20,"eeee"); >> left join ------------- select a.id,a.name,b.dept_id from emp a left join emp_dept b on (a.id=b.emp_id); # 挑出左边的 table emp 中的所有资料,即使 emp_dept 中没有的资料也挑出来,没有的就用 NULL 来显示, # 也即显示资料是以左边的 table emp 中的资料为基础 mysql> select a.id,a.name,b.dept_id -> from emp a left join emp_dept b on (a.id=b.emp_id); +----+-----------+---------+ | id | name | dept_id | +----+-----------+---------+ | 1 | Dennis-1 | R&D | | 2 | Dennis-2 | DEv | | 3 | Dennis-3 | R&D | | 4 | Dennis-4 | Test | | 5 | Dennis-5 | Test | | 6 | Dennis-6 | NULL | | 7 | Dennis-7 | NULL | | 8 | Dennis-8 | NULL | | 9 | Dennis-9 | NULL | | 10 | Dennis-10 | NULL | +----+-----------+---------+ # 挑出 table emp 中有而 table emp_dept 中没有的人员资料 select a.id,a.name,b.dept_id from emp a left join emp_dept b on (a.id=b.emp_id) where b.dept_id IS NULL; mysql> select a.id,a.name,b.dept_id -> from emp a left join emp_dept b on (a.id=b.emp_id) -> where b.dept_id IS NULL; +----+-----------+---------+ | id | name | dept_id | +----+-----------+---------+ | 6 | Dennis-6 | NULL | | 7 | Dennis-7 | NULL | | 8 | Dennis-8 | NULL | | 9 | Dennis-9 | NULL | | 10 | Dennis-10 | NULL | +----+-----------+---------+ # 把 table emp_dept 放在左边的情形(当然以 emp_dept 中的数据为基础来显示资料,emp 中比emp_dept 中多的资料也就不会显示出来了): select a.id,a.name,b.dept_id from emp_dept b left join emp a on (a.id=b.emp_id); mysql> select a.id,a.name,b.dept_id -> from emp_dept b left join emp a on (a.id=b.emp_id); +------+----------+---------+ | id | name | dept_id | +------+----------+---------+ | NULL | NULL | dddd | | 2 | Dennis-2 | DEv | | 1 | Dennis-1 | R&D | | 3 | Dennis-3 | R&D | | 4 | Dennis-4 | Test | | 5 | Dennis-5 | Test | +------+----------+---------+ >> right join --------------- select a.id,a.name,b.dept_id from emp a right join emp_dept b on (a.id=b.emp_id); # 挑资料时以右边 table emp_dept 中的资料为基础来显示资料 mysql> select a.id,a.name,b.dept_id -> from emp a right join emp_dept b on (a.id=b.emp_id); +------+----------+---------+ | id | name | dept_id | +------+----------+---------+ | NULL | NULL | dddd | | 2 | Dennis-2 | DEv | | 1 | Dennis-1 | R&D | | 3 | Dennis-3 | R&D | | 4 | Dennis-4 | Test | | 5 | Dennis-5 | Test | +------+----------+---------+ 6 rows in set (0.00 sec) # 我们再把 table 的位置交换一下,再用 right join 试试 select a.id,a.name,b.dept_id from emp_dept b right join emp a on (a.id=b.emp_id); mysql> select a.id,a.name,b.dept_id -> from emp_dept b right join emp a on (a.id=b.emp_id); +----+-----------+---------+ | id | name | dept_id | +----+-----------+---------+ | 1 | Dennis-1 | R&D | | 2 | Dennis-2 | DEv | | 3 | Dennis-3 | R&D | | 4 | Dennis-4 | Test | | 5 | Dennis-5 | Test | | 6 | Dennis-6 | NULL | | 7 | Dennis-7 | NULL | | 8 | Dennis-8 | NULL | | 9 | Dennis-9 | NULL | | 10 | Dennis-10 | NULL | +----+-----------+---------+ # 是不是和 left join 一样了? >> inner join STRAIGHT_JOIN select a.id,a.name,b.dept_id from emp a ,emp_dept b where a.id=b.emp_id; mysql> select a.id,a.name,b.dept_id -> from emp a ,emp_dept b -> where a.id=b.emp_id; +----+----------+---------+ | id | name | dept_id | +----+----------+---------+ | 2 | Dennis-2 | DEv | | 1 | Dennis-1 | R&D | | 3 | Dennis-3 | R&D | | 4 | Dennis-4 | Test | | 5 | Dennis-5 | Test | +----+----------+---------+ 2.9.3. 别名 alias 你可以在GROUP BY、ORDER BY或在HAVING部分中使用别名引用列。别名也可以用来为列取一个更好点的名字: SELECT SQRT(a*b) as rt FROM table_name GROUP BY rt HAVING rt > 0; SELECT id,COUNT(*) AS cnt FROM table_name GROUP BY id HAVING cnt > 0; SELECT id AS "Customer identity" FROM table_name; 注意,你的 ANSI SQL 不允许你在一个WHERE子句中引用一个别名。这是因为在WHERE代码被执行时,列值还可能没有终结。例如下列查询是不合法: SELECT id,COUNT(*) AS cnt FROM table_name WHERE cnt > 0 GROUP BY id; WHERE语句被执行以确定哪些行应该包括GROUP BY部分中,而HAVING用来决定应该只用结果集合中的哪些行。 2.9.4. 正则 正则表达式(regex)是定义复杂查询的一个强有力的工具。 这里是一个简单的资料,它忽略了一些详细的信息。 正则表达式定义了一个字符串的规则。最简单的正则表达式不包含任何保留字。例如, 正则表达式hello只和字符串“hello”匹配。 一般的正则表达式使用了某些特殊的结构,所以它能匹配更多的字符串。例如,正则 表达式hello|word既能匹配字符串“hello”也能匹配字符串“word”。 举一个更复杂一点的例子,正则表达式B[an]*s可以匹配字符串“Bananas”、“Baaaaa s” 、“Bs”以及其他任何以B开头以s结尾的字符串,中间可以包括任意个a和任意个n的组 合。 一个正则表达式中的可以使用以下保留字 ^ 所匹配的字符串以后面的字符串开头 mysql> select "fonfo" REGEXP "^fo$"; -> 0(表示不匹配) mysql> select "fofo" REGEXP "^fo"; -> 1(表示匹配) $ 所匹配的字符串以前面的字符串结尾 mysql> select "fono" REGEXP "^fono$"; -> 1(表示匹配) mysql> select "fono" REGEXP "^fo$"; -> 0(表示不匹配) .. 匹配任何字符(包括新行) mysql> select "fofo" REGEXP "^f.*"; -> 1(表示匹配) mysql> select "fonfo" REGEXP "^f.*"; -> 1(表示匹配) a* 匹配任意0-n多个a(包括空串) mysql> select "Ban" REGEXP "^Ba*n"; -> 1(表示匹配) mysql> select "Baaan" REGEXP "^Ba*n"; -> 1(表示匹配) mysql> select "Bn" REGEXP "^Ba*n"; -> 1(表示匹配) a+ 匹配任意1-n多个a(不包括空串) mysql> select "Ban" REGEXP "^Ba+n"; -> 1(表示匹配) mysql> select "Bn" REGEXP "^Ba+n"; -> 0(表示不匹配) a? 匹配0-1个a mysql> select "Bn" REGEXP "^Ba?n"; -> 1(表示匹配) mysql> select "Ban" REGEXP "^Ba?n"; -> 1(表示匹配) mysql> select "Baan" REGEXP "^Ba?n"; -> 0(表示不匹配) de|abc 匹配de或abc mysql> select "pi" REGEXP "pi|apa"; -> 1(表示匹配) mysql> select "axe" REGEXP "pi|apa"; -> 0(表示不匹配) mysql> select "apa" REGEXP "pi|apa"; -> 1(表示匹配) mysql> select "apa" REGEXP "^(pi|apa)$"; -> 1(表示匹配) mysql> select "pi" REGEXP "^(pi|apa)$"; -> 1(表示匹配) mysql> select "pix" REGEXP "^(pi|apa)$"; -> 0(表示不匹配) (abc)* 匹配任意多个(0-n个)abc(包括空串) mysql> select "pi" REGEXP "^(pi)*$"; -> 1(表示匹配) mysql> select "pip" REGEXP "^(pi)*$"; -> 0(表示不匹配) mysql> select "pipi" REGEXP "^(pi)*$"; -> 1(表示匹配) {1} {2,3} 这是一个更全面的方法,它可以实现前面好几种保留字的功能 a* 可以写成a{0,} a+ 可以写成a{1,} a? 可以写成a{0,1} 在{}内只有一个整型参数i,表示字符只能出现i次;在{}内有一个整型参数i, 后面跟一个“,”,表示字符可以出现i次或i次以上;在{}内只有一个整型参数i, 后面跟一个“,”,再跟一个整型参数j,表示字符只能出现i次以上,j次以下 (包括i次和j次)。其中的整型参数必须大于等于0,小于等于 RE_DUP_MAX(默认是25 5)。 如果有两个参数,第二个必须大于等于第一个 [a-dX] 匹配“a”、“b”、“c”、“d”或“X” [^a-dX] 匹配除“a”、“b”、“c”、“d”、“X”以外的任何字符。 “[”、“]”必须成对使用 mysql> select "aXbc" REGEXP "[a-dXYZ]"; -> 1(表示匹配) mysql> select "aXbc" REGEXP "^[a-dXYZ]$"; -> 0(表示不匹配) mysql> select "aXbc" REGEXP "^[a-dXYZ]+$"; -> 1(表示匹配) mysql> select "aXbc" REGEXP "^[^a-dXYZ]+$"; -> 0(表示不匹配) mysql> select "gheis" REGEXP "^[^a-dXYZ]+$"; -> 1(表示匹配) mysql> select "gheisa" REGEXP "^[^a-dXYZ]+$"; -> 0(表示不匹配) ------------------------------------------------------------ [[.characters.]] 表示比较元素的顺序。在括号内的字符顺序是唯一的。但是括号中可以包含通配符, 所以他能匹配更多的字符。举例来说:正则表达式[[.ch.]]*c匹配chchcc的前五个字符 。 [=character_class=] 表示相等的类,可以代替类中其他相等的元素,包括它自己。例如,如果o和(+)是 一个相等的类的成员,那么[[=o=]]、[[=(+)=]]和[o(+)]是完全等价的。 [:character_class:] 在括号里面,在[:和:]中间是字符类的名字,可以代表属于这个类的所有字符。 字符类的名字有: alnum、digit、punct、alpha、graph、space、blank、lower、uppe r、cntrl、print和xdigit mysql> select "justalnums" REGEXP "[[:alnum:]]+"; -> 1(表示匹配) mysql> select "!!" REGEXP "[[:alnum:]]+"; -> 0(表示不匹配) [[:<:]] [[:>:]] 分别匹配一个单词开头和结尾的空的字符串,这个单词开头和结尾都不是包含在alnum中 的字符也不能是下划线。 mysql> select "a word a" REGEXP "[[:<:]]word[[:>:]]"; -> 1(表示匹配) mysql> select "a xword a" REGEXP "[[:<:]]word[[:>:]]"; -> 0(表示不匹配) mysql> select "weeknights" REGEXP "^(wee|week)(knights|nights)$"; -> 1(表示 匹配) 2.9.5. Select 中使用 IF Statement mysql> select * from test; +------+------+------+-------+ | dept | id | sex | name | +------+------+------+-------+ | 1 | 1 | 0 | wang | | 2 | 2 | 1 | zhang | | 3 | 3 | 0 | li | +------+------+------+-------+ 3 rows in set (0.00 sec) mysql> select dept,id,if(sex=0,'女','男') sex,name from test; +------+------+-----+-------+ | dept | id | sex | name | +------+------+-----+-------+ | 1 | 1 | 女 | wang | | 2 | 2 | 男 | zhang | | 3 | 3 | 女 | li | +------+------+-----+-------+ 3 rows in set (0.00 sec) 2.9.6. Select中使用CASE Statement mysql> select dept,id,(case sex when '0' then '女' else '男' end) as sex,name from test; +------+------+------+-------+ | dept | id | sex | name | +------+------+------+-------+ | 1 | 1 | 女 | wang | | 2 | 2 | 男 | zhang | | 3 | 3 | 女 | li | +------+------+------+-------+ mysql> select (case dept when '1' then 'no1' when '2' then 'no2' else 'other' end) as dept from test; +-------+ | dept | +-------+ | no1 | | no2 | | other | +-------+ 3 rows in set (0.00 sec) 注意: 相当于Oracle 中的decode 和case when 在统计报表中很有用处 2.10. 存储过程和函数 CREATE PROCEDURE sp_name ([proc_parameter[,...]]) [characteristic ...] routine_body CREATE FUNCTION sp_name ([func_parameter[,...]]) RETURNS type [characteristic ...] routine_body proc_parameter: [ IN | OUT | INOUT ] param_name type func_parameter: param_name type type: Any valid MySQL data type characteristic: LANGUAGE SQL | [NOT] DETERMINISTIC | { CONTAINS SQL | NO SQL | READS SQL DATA | MODIFIES SQL DATA } | SQL SECURITY { DEFINER | INVOKER } | COMMENT 'string' routine_body: Valid SQL procedure statement or statements 例子:创建一个过程hello,显示问候语 mysql> delimiter ; mysql> drop PROCEDURE if exists hello; Query OK, 0 rows affected (0.00 sec) mysql> delimiter // mysql> mysql> CREATE PROCEDURE hello (IN s varchar(20)) -> BEGIN -> SELECT CONCAT('Hello,',s,'!') as hello; -> END; -> // Query OK, 0 rows affected (0.00 sec) mysql> delimiter ; mysql> call hello('wangyl'); +---------------+ | hello | +---------------+ | Hello,wangyl! | +---------------+ 1 row in set (0.00 sec) Query OK, 0 rows affected (0.00 sec) 例子2: 查询t表的记录总数 mysql> delimiter // mysql> CREATE PROCEDURE simpleproc (OUT param1 INT) -> BEGIN -> SELECT COUNT(*) INTO param1 FROM t; -> END -> // Query OK, 0 rows affected (0.00 sec) mysql> delimiter ; mysql> CALL simpleproc(@a); Query OK, 0 rows affected (0.00 sec) mysql> SELECT @a; +------+ | @a | +------+ | 3 | +------+ 1 row in set (0.00 sec) 例子:创建一个函数 mysql> delimiter ; mysql> drop FUNCTION if exists dateFunction; Query OK, 0 rows affected (0.00 sec) mysql> delimiter // mysql> CREATE FUNCTION dateFunction (iCase int) -> RETURNS varchar(50) -> begin -> DECLARE iType int; -> DECLARE sReturn varchar(50); -> set iType =icase +1; -> case iType -> when 1 then select DATE_FORMAT(NOW(),'%Y-%m-%d') into sReturn; -> when 2 then select DATE_FORMAT(NOW(),'%W %M %Y') into sReturn; -> else -> select NOW() into sReturn; -> end case; -> return sReturn; -> end; -> // Query OK, 0 rows affected (0.00 sec) mysql> delimiter ; mysql> select dateFunction(0); +-----------------+ | dateFunction(0) | +-----------------+ | 2005-11-14 | +-----------------+ 1 row in set (0.00 sec) mysql> select dateFunction(1); +----------------------+ | dateFunction(1) | +----------------------+ | Monday November 2005 | +----------------------+ 1 row in set (0.00 sec) mysql> select dateFunction(2); +---------------------+ | dateFunction(2) | +---------------------+ | 2005-11-14 15:05:43 | +---------------------+ 1 row in set (0.00 sec) 2.11. 补充:trigger CREATE TRIGGER trigger_name trigger_time trigger_event ON tbl_name FOR EACH ROW trigger_stmt CREATE TABLE test1(a1 INT); CREATE TABLE test2(a2 INT); CREATE TABLE test3(a3 INT NOT NULL AUTO_INCREMENT PRIMARY KEY); CREATE TABLE test4( a4 INT NOT NULL AUTO_INCREMENT PRIMARY KEY, b4 INT DEFAULT 0 ); DELIMITER | CREATE TRIGGER testref BEFORE INSERT ON test1 FOR EACH ROW BEGIN INSERT INTO test2 SET a2 = NEW.a1; DELETE FROM test3 WHERE a3 = NEW.a1; UPDATE test4 SET b4 = b4 + 1 WHERE a4 = NEW.a1; END| DELIMITER ; INSERT INTO test3 (a3) VALUES (NULL), (NULL), (NULL), (NULL), (NULL), (NULL), (NULL), (NULL), (NULL), (NULL); INSERT INTO test4 (a4) VALUES (0), (0), (0), (0), (0), (0), (0), (0), (0), (0); If you insert the following values into table test1 as shown here: mysql> INSERT INTO test1 VALUES -> (1), (3), (1), (7), (1), (8), (4), (4); Query OK, 8 rows affected (0.01 sec) Records: 8 Duplicates: 0 Warnings: 0 Then the data in the four tables will be as follows: mysql> SELECT * FROM test1; +------+ | a1 | +------+ | 1 | | 3 | | 1 | | 7 | | 1 | | 8 | | 4 | | 4 | +------+ 8 rows in set (0.00 sec) mysql> SELECT * FROM test2; +------+ | a2 | +------+ | 1 | | 3 | | 1 | | 7 | | 1 | | 8 | | 4 | | 4 | +------+ 8 rows in set (0.00 sec) mysql> SELECT * FROM test3; +----+ | a3 | +----+ | 2 | | 5 | | 6 | | 9 | | 10 | +----+ 5 rows in set (0.00 sec) mysql> SELECT * FROM test4; +----+------+ | a4 | b4 | +----+------+ | 1 | 3 | | 2 | 0 | | 3 | 1 | | 4 | 2 | | 5 | 0 | | 6 | 0 | | 7 | 1 | | 8 | 1 | | 9 | 0 | | 10 | 0 | +----+------+ 10 rows in set (0.00 sec) 2.12. 删除 DELETE Syntax Single-table syntax: DELETE [LOW_PRIORITY] [QUICK] [IGNORE] FROM tbl_name [WHERE where_condition] [ORDER BY ...] [LIMIT row_count] Multiple-table syntax: DELETE [LOW_PRIORITY] [QUICK] [IGNORE] tbl_name[.*] [, tbl_name[.*]] ... FROM table_references [WHERE where_condition] Or: DELETE [LOW_PRIORITY] [QUICK] [IGNORE] FROM tbl_name[.*] [, tbl_name[.*]] ... USING table_references [WHERE where_condition] 对于删除多个表,不能使用order by 和limit 多表删除语法一: ,只是在删除 在from 前面的表所中匹配的记录 DELETE t1, t2 FROM t1, t2, t3 WHERE t1.id=t2.id AND t2.id=t3.id; 从t1,t2,t3 表选出要删除的记录,只是删除t1,t2 表中所匹配得这些记录. 多表删除语法二: 在from 列出的表中删除选中的记录. DELETE FROM t1, t2 USING t1, t2, t3 WHERE t1.id=t2.id AND t2.id=t3.id; 从t1,t2,t3 表选出要删除的记录(使用using ),只是删除t1,t2 表中所匹配得这些记录. 注意: 如果您使用一个别名,您必须使用别名. DELETE t1 FROM test AS t1, test2 WHERE ... 支持多个数据之间的多表删除,但是在这种情况下,你必须指定表,而不能使用别名: DELETE test1.tmp1, test2.tmp2 FROM test1.tmp1, test2.tmp2 WHERE ... 当前,您不能从相同表的子查询中,删除同一表的数据. July 19 JDOM 介绍及使用指南一、JDOM 简介 JDOM是一个开源项目,它基于树型结构,利用纯JAVA的技术对XML文档实现解析、生成、序列化以及多种操作。 JDOM 直接为JAVA编程服务。它利用更为强有力的JAVA语言的诸多特性(方法重载、集合概念以及映射),把SAX和DOM的功能有效地结合起来。 在使用设计上尽可能地隐藏原来使用XML过程中的复杂性。利用JDOM处理XML文档将是一件轻松、简单的事。 JDOM 在2000年的春天被Brett McLaughlin和Jason Hunter开发出来,以弥补DOM及SAX在实际应用当中的不足之处。 这些不足之处主要在于SAX没有文档修改、随机访问以及输出的功能,而对于DOM来说,JAVA程序员在使用时来用起来总觉得不太方便。 DOM的缺点主要是来自于由于Dom是一个接口定义语言(IDL),它的任务是在不同语言实现中的一个最低的通用标准,并不是为JAVA特别设计的。JDOM的最新版本为JDOM Beta 9。最近JDOM被收录到JSR-102内,这标志着JDOM成为了JAVA平台组成的一部分。 二、JDOM 包概览 JDOM是由以下几个包组成的 org.JDOM org.JDOM.input org.JDOM.output org.JDOM.adapters org.JDOM.transform 三、JDOM 类说明 org.JDOM 这个包里的类是你解析xml文件后所要用到的所有数据类型。 Attribute CDATA Coment DocType Document Element EntityRef Namespace ProscessingInstruction Text org.JDOM.transform 在涉及xslt格式转换时应使用下面的2个类 JDOMSource JDOMResult org.JDOM.input 输入类,一般用于文档的创建工作 SAXBuilder DOMBuilder ResultSetBuilder org.JDOM.output 输出类,用于文档转换输出 XMLOutputter SAXOutputter DomOutputter JTreeOutputter 使用前注意事项: 1.JDOM对于JAXP 以及 TRax 的支持 JDOM 支持JAXP1.1:你可以在程序中使用任何的parser工具类,默认情况下是JAXP的parser。 制定特别的parser可用如下形式 SAXBuilder parser = new SAXBuilder("org.apache.crimson.parser.XMLReaderImpl"); Document doc = parser.build("http://www.cafeconleche.org/"); // work with the document... JDOM也支持TRaX:XSLT可通过JDOMSource以及JDOMResult类来转换(参见以后章节) 2.注意在JDOM里文档(Document)类由org.JDOM.Document 来表示。这要与org.w3c.dom中的Document区别开,这2种格式如何转换在后面会说明。 以下如无特指均指JDOM里的Document。 四、JDOM主要使用方法 1.Ducument类 (1)Document的操作方法: Element root = new Element("GREETING"); Document doc = new Document(root); root.setText("Hello JDOM!"); 或者简单的使用Document doc = new Document(new Element("GREETING").setText("Hello JDOM!t")); 这点和DOM不同。Dom则需要更为复杂的代码,如下: DocumentBuilderFactory factory =DocumentBuilderFactory.newInstance(); DocumentBuilder builder =factory.newDocumentBuilder(); Document doc = builder.newDocument(); Element root =doc.createElement("root"); Text text = doc.createText("This is the root"); root.appendChild(text); doc.appendChild(root); 注意事项:JDOM不允许同一个节点同时被2个或多个文档相关联,要在第2个文档中使用原来老文档中的节点的话。首先需要使用detach()把这个节点分开来。 (2)从文件、流、系统ID、URL得到Document对象: DOMBuilder builder = new DOMBuilder(); Document doc = builder.build(new File("jdom_test.xml")); SAXBuilder builder = new SAXBuilder(); Document doc = builder.build(url); 在新版本中DOMBuilder 已经Deprecated掉 DOMBuilder.builder(url),用SAX效率会比较快。 这里举一个小例子,为了简单起见,使用String对象直接作为xml数据源: public jdomTest() { String textXml = null; textXml = "<note>"; textXml = textXml + "<to>aaa</to><from>bbb</from><heading>ccc</heading><body>ddd</body>"; textXml = textXml + "</note>"; SAXBuilder builder = new SAXBuilder(); Document doc = null; Reader in= new StringReader(textXml); try { doc = builder.build(in); Element root = doc.getRootElement(); List ls = root.getChildren();//注意此处取出的是root节点下面的一层的Element集合 for (Iterator iter = ls.iterator(); iter.hasNext(); ) { Element el = (Element) iter.next(); if(el.getName().equals("to")){ System.out.println(el.getText()); } } } catch (IOException ex) { ex.printStackTrace(); } catch (JDOMException ex) { ex.printStackTrace(); } } 很简单把。 (3)DOM的document和JDOM的Document之间的相互转换使用方法,简单! DOMBuilder builder = new DOMBuilder(); org.jdom.Document jdomDocument = builder.build(domDocument); // work with the JDOM document… DOMOutputter converter = new DOMOutputter(); org.w3c.dom.Document domDocument = converter.output(jdomDocument); // work with the DOM document… 2.XML文档输出 XMLOutPutter类: JDOM的输出非常灵活,支持很多种io格式以及风格的输出 Document doc = new Document(...); XMLOutputter outp = new XMLOutputter(); // Raw output outp.output(doc, fileOutputStream); // Compressed output outp.setTextTrim(true); outp.output(doc, socket.getOutputStream()); // Pretty output outp.setIndent(" "); outp.setNewlines(true); outp.output(doc, System.out); ...... 详细请参阅最新的JDOM API手册 3.Element 类: (1)浏览Element树 //获得根元素element Element root = doc.getRootElement(); // 获得所有子元素的一个list List allChildren = root.getChildren(); // 获得指定名称子元素的list List namedChildren = root.getChildren("name"); //获得指定名称的第一个子元素 Element child = root.getChild("name"); (这里的List是java.util.List) JDOM给了我们很多很灵活的使用方法来管理子元素 List allChildren = root.getChildren(); // 删除第四个子元素 allChildren.remove(3); // 删除叫“jack”的子元素 allChildren.removeAll(root.getChildren("jack")); root.removeChildren("jack"); // 便捷写法 // 加入 allChildren.add(new Element("jane")); root.addContent(new Element("jane")); // 便捷写法 allChildren.add(0, new Element("first")); (2)移动Elements: 在JDOM里很简单 Element movable = new Element("movable"); parent1.addContent(movable); // place parent1.removeContent(movable); // remove parent2.addContent(movable); // add 在Dom里 Element movable = doc1.createElement("movable"); parent1.appendChild(movable); // place parent1.removeChild(movable); // remove parent2.appendChild(movable); // 出错! 补充: 纠错性 JDOM的Element构造函数(以及它的其他函数)会检查element是否合法。 而它的add/remove方法会检查树结构,检查内容如下: 1.在任何树中是否有回环节点 2.是否只有一个根节点 3.是否有一致的命名空间(Namespaces) (3)Element的text内容读取 <description> A cool demo </description> // The text is directly available // Returns "\n A cool demo\n" String desc = element.getText(); // There's a convenient shortcut // Returns "A cool demo" String desc = element.getTextTrim(); (4)Elment内容修改 element.setText("A new description"); 3.可正确解释特殊字符 element.setText("<xml> content"); 4.CDATA的数据写入、读出 element.addContent(new CDATA("<xml> content")); String noDifference = element.getText(); 混合内容 element可能包含很多种内容,比如说 <table> <!-- Some comment --> Some text <tr>Some child element</tr> </table> 取table的子元素tr String text = table.getTextTrim(); Element tr = table.getChild("tr"); 也可使用另外一个比较简单的方法 List mixedCo = table.getContent(); Iterator itr = mixedCo.iterator(); while (itr.hasNext()) { Object o = i.next(); if (o instanceof Comment) { ... } // 这里可以写成Comment, Element, Text, CDATA,ProcessingInstruction, 或者是EntityRef的类型 } // 现在移除Comment,注意这里游标应为1。这是由于回车键也被解析成Text类的缘故,所以Comment项应为1。 mixedCo.remove(1); 4.Attribute类 <table width="100%" border="0"> </table> //获得attribute String width = table.getAttributeValue("width"); int border = table.getAttribute("width").getIntValue(); //设置attribute table.setAttribute("vspace", "0"); // 删除一个或全部attribute table.removeAttribute("vspace"); table.getAttributes().clear(); 5.处理指令(Processing Instructions)操作 一个Pls的例子 <?br?> <?cocoon-process type="xslt"?> | | | | 目标 数据 处理目标名称(Target) String target = pi.getTarget(); 获得所有数据(data),在目标(target)以后的所有数据都会被返回。 String data = pi.getData(); 获得指定属性的数据 String type = pi.getValue("type"); 获得所有属性的名称 List ls = pi.getNames(); 6.命名空间操作 <xhtml:html xmlns:xhtml="http://www.w3.org/1999/xhtml"> <xhtml:title>Home Page</xhtml:title> </xhtml:html> Namespace xhtml = Namespace.getNamespace("xhtml", "http://www.w3.org/1999/xhtml"); List kids = html.getChildren("title", xhtml); Element kid = html.getChild("title", xhtml); kid.addContent(new Element("table", xhtml)); 7.XSLT格式转换 使用以下函数可对XSLT转换 最后如果你需要使用w3c的Document则需要转换一下。 public static Document transform(String stylesheet,Document in) throws JDOMException { try { Transformer transformer = TransformerFactory.newInstance() .newTransformer(new StreamSource(stylesheet)); JDOMResult out = new JDOMResult(); transformer.transform(new JDOMSource(in), out); return out.getDeocument(); } catch (TransformerException e) { throw new JDOMException("XSLT Trandformation failed", e); } } 参考书目: 1.JDOM官方网站: http://www.jdom.org 2.<<Processing XML with Java>> Elliotte Rusty Harold 2002 3.JDOM API Documentation 4.<<JDOM Makes XML Easy>>Jason Hunter Co-Creator JDOM Project 5.WSDP Tutorial |
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|