📄 037.htm
字号:
<p>Table1.SetKey; {将Table1置成查找状态}</p>
<p>Table1.Field[0].AsString := Edit1.Text; {指定查找值}</p>
<p>Table1.GotoKey; {进行查找}</p>
<p> </p>
<p>上面最后一行代码是根据用户指定的查找值,在表中执行查找。查找的结果有两种,也许成功也许失败,这是由调用GotoKey方法之后返回的布尔值来决定,如果返回True,那么查找成功,并且记录指针会指向与查找值匹配的记录,如果返回Fale,那么查找失败,记录指针的位置不发生变化。下面的代码可以测试调用GotoKey方法之后的返回值,告知用户查找是否成功。</p>
<p> </p>
<p>Table1.SetKey;</p>
<p>Table1.Field[0].AsString:= 'Smith';</p>
<p>If not Table1.GotoKey then</p>
<p>ShowMessage('记录没找到')</p>
<p> </p>
<p>在这一段代码中,如果在表中没有找到第一个字段值为Smith的记录,该应用程序会弹出一个对话框告知用户“记录没有找到”。</p>
<p>如果在表中存在多个关键字段或辅助索引中包含多个字段时,你在进行查找时,只想为第一个字段指定查找值,那么必须要设置TTable部件的KeyFieldCount的属性值为1。如果想为多个字段指定查找值,只能为相邻的字段指定查找值,例如辅助索引中共有三个字段,那么我们只能为第一个字段、第一和第二个字段、第一和第二以及第三个字段指定查找值,而不能为第一和第三个字段指定查找值。</p>
<p>GotoNearest方法的使用与GotoKey方法完全一样,只是它用于不精确查找,它不要求查找结果与查找值精确匹配,当表中有与查找值精确匹配的记录时,它将记录指针移到该记录处,当表中没有与查找值精确匹配的记录时,它会查找出与查找值最接近的记录,并将记录指针移到该记录处。</p>
<p>下面是应用GotoNearest方法的一段代码:</p>
<p> </p>
<p>Table1.SetKey;</p>
<p>Table1.Fields[0].AsString:= 'Sm';</p>
<p>Table1.GotoNearest;</p>
<p> </p>
<p>执行上述代码后,若表中存在第一个字段值等于Sm的记录时,记录指针将移到该记录处,若表中不存在第一个字段值等于Sm的记录,而存在第一个字段值等于Smith的记录,那么记录指针会移到该记录处。</p>
<p>如果我们不是以数据库表中的关键字段作为查找字段,我们也可以为TTable部件的IndexFieldName属性中的字段或IndexName属性中的字段指定查找值进行数据查找。例如,假设Customer表中有一个名叫CityIndex的辅助索引,我们为CityIndex中的字段指定查找值进行查找时,首先设置TTable部件的IndexName属性为CityIndex,然后再进行查找,下面是具体的程序代码:</p>
<p> </p>
<p>Table1.IndexName := 'CityIndex';</p>
<p>Table1.Open;</p>
<p>Table1.SetKey;</p>
<p>Table1.FieldByName{'City').AsString := Edit1.Text;</p>
<p>Table1.GotoKey;</p>
<p> </p>
<p>使用Find方式:使用Find方式在数据库中进行数据查找的方法有:FindNearest方法和FindKey方法。</p>
<p>FindKey方法和FindNearest方法为数据查找提供了一个简单的方法,它们将SetKey、指定查找值、执行查找三个步骤融合在一步里完成,它们在指定查找值时,是把各字段的查找值组成一个数组传给FindKey或FindNearest。下面是使FindKey方法的一个例子。</p>
<p>假设Tabel1对应的表中的第一个字段是关键字段。</p>
<p> </p>
<p>Table.FindKey([Edit1.Text]);</p>
<p> </p>
<p>如果用GotoKey方法完成这一功能则需要编写下面代码:</p>
<p> </p>
<p>Table1.SetKey;</p>
<p>Table1.Fields[0].AsStrine := Edit.Text;</p>
<p>Table1.GotoKey;</p>
<p> </p>
<p>FindKey方法和FindNearest方法的区别与GotoKey和GotoNearest方法的区别是一样的。</p>
<p> </p>
<p>15.4.2.3 创建主要──明细数据库应用</p>
<p> </p>
<p>TTable部件中MasterSource属性和MasterFields属性是用于定义两个数据库表的一对多的关系。MasterSource属性指定主表对应的TDataSource部件,MasterFields属性指定主表和明细表之间建立联系的字段,主表和明细表之间建立一对多关系时,可能不只是基于一个字段,可能有多个字段。如果有多个字段,那么在说明MasterFields属性时,多个字段之间要用分号隔开。如Table1.MasterFields
:= 'OrderNo;CustNo'。在设计阶段可以使用字段连接设计器(Field Link
Designer)为两上表创建一对多的关系,在Object Inspector 中双击TTable部件的MasterFields便可以打开Field
Link Designer,进行一对多关系的创建。 如创建Customer.DB表和Order.DB表之间的一对多关系时,使用Field
Link Designer 如图15.5所示。</p>
<p> </p>
<p align="center"> </p>
<p> </p>
<p>图15.5 使用Field Link Designer创建一对多关系</p>
<p> </p>
<p>Field Link Designer提供了一种可视化的方法来创建主要──明细表之间的一对多关系。图中Available
Indexes组合框中存放着明细表中的关键字段和索引字段,可以选择索引字段进行连接。在主表中选择一个用于连接的关键字段,然后将其与明细表中相应的关键字段连接,单击Add按钮,主要──明细表的连接字段将显示在Joined
Fields列表框中,如:</p>
<p>CustNo->CustNo </p>
<p align="center">15.5 TDataSource部件及其应用</p>
<p> </p>
<p>TDataSource部件是开发数据库应用程序中用到的非常重要的部件,它是连接数据集部件TTable或TQuery和数据浏览部件的桥梁。TDataSource部件本身十分简单,它所拥有的属性、事件和方法都比较少,在使用该部件时无需作太多的工作,它主要是为数据浏览部件服务的,如果在应用程序中没有使用数据浏览部件,我们也没有必要为应用程序设置TDataSource部件。</p>
<p> </p>
<p>15.5.1 TDataSource部件的属性</p>
<p> </p>
<p>TDataSource部件除了其他部件都拥有的Name属性和Tag属性之外,主要有下面几个属性:</p>
<p>DataSet属性:该属性说明TDataSource部件从中获取数据的数据集的名字,它可以是TTable部件的名字,也可以是TQuery部件的名字,甚至还可以指定其他窗体内的数据集作为该属性的值,如在下面的程序中我们指定窗体Form2中的table1作为窗体Form1中的DataSource1的DataSet属性值:</p>
<p> </p>
<p>TForm1.Formcreate(Sender : Tobject);</p>
<p>Begin</p>
<p>DataSource1.DataSet := Form2.Table1;</p>
<p>end;</p>
<p> </p>
<p>Enable属性:Enable属性可以暂时性地切断TDataSource部件和与之相连的数据集部件的连接。这是一个布尔型变量。当它的值为False时,TDataSource部件和数据集部件的连接被切断,且所有与TDataSource部件相连的数据浏览部件中将变为一片空白,不显示任何数据信息。当Enabled的值变为True时,TDataSource部件和数据集部件的连接恢复,且与TDataSource部件相连的数据浏览部件恢复显示数据。不过要实现上述这些功能,一般不使用TDataSource部件的Enabled属性,而是调用数据集部件的DisableControls方法和EnableControls
方法,因为调用这两个方法可以方便地控制与数据集部件相连的所有TDataSource部件以及与TDataSource部件相连的数据浏览部件。</p>
<p>AutoEdit属性:这是一个布尔型变量,它用于说明是否将与TDataSource部件相连的数据集置于编辑状态。当AutoEdit的值为True时,应用程序运行时,与TDataSource相连的数据集部件自动地被设置成编辑状态,当用户在与TDataSource部件相连的数据浏览部件中输入新的值时,数据集部件中的记录也随之改变。如果AutoEdit的值为False,用户想通过数据浏览部件或程序修改数据集中的记录,必须要调用数据集部件的Edit方法,将其置为编辑状态之后才能够进行。</p>
<p> </p>
<p>15.5.2 TDataSource部件的事件</p>
<p> </p>
<p>TDataSource部件具有三个事件:</p>
<p>● OnDataChange事件</p>
<p>● OnStateChange</p>
<p>● OnUpdataData</p>
<p> </p>
<p>OnDataChange事件:当与TDataSource相连的数据集中的记录指针的位置发生改变时,该事件就被触发,也就是说当程序调用数据集部件的Next、Previous、Insert、Append等方法导致记录指针的位置发生改变时,便会触发该事件。该事件一般用于保持应用中多个部件之间的同步。</p>
<p>OnUpdataData事件:当数据集部件中当前记录将要被修改时,触发该事件。例如在程序调用post方法之后但在修改后的数据记录真正被写回磁盘中的数据库文件之前触发该事件,在应用中使用非数据浏览部件时要它与数据集保持同步时常使用该事件进行相关的处理。</p>
<p>OnStateChange事件:当与TDataSource部件相连的数据集部件的状态发生改变时,
便触发该事件。因为数据集部件的State属性标明了数据集部件当前所处的状态,当数据集的状态发生变化时,使用该事件进行有关的处理是很有用的,在一个具体的应用中,
数据集部件的状态常常是频繁地变化的,为了跟踪数据集部件的状态变化,
可以用下面例子中的程序代码将数据集部件当前的状态显示在一个标签上:</p>
<p> </p>
<p>TForm1.DataSource1OnStateChange(Sender : Tobject);</p>
<p>var</p>
<p>S : String;</p>
<p>begin</p>
<p>Case Table1,State of </p>
<p>dsInactive : S := 'Inactive';</p>
<p>dsBrowse : S := 'Browse';</p>
<p>dsEdit : S := 'Edit';</p>
<p>dsInsert : S := 'SetKey';</p>
<p>dsSetKey : S := 'SetKey';</p>
<p>end;</p>
<p>Label1.Caption := S;</p>
<p>end;</p>
<p> </p>
<p>类似地我们也可以通过检测数据集部件的状态来控制有关的按钮和菜单项是否有效。
例如:在一个应用窗体中有一个InsertBtn按钮,用于控制向数据集部件table1对应的数据库表中插入记录;还有一个CancelBtn按钮用于控制是否取消用户对当前记录的修改或插入新记录。下面的程序代码根据Table1的状态来控制这两个按钮的功能(是否有效,在窗体是否变灰暗)。</p>
<p> </p>
<p>Form1.DataSource1OnStateChange(Sender : Tobject);</p>
<p>begin</p>
<p>InsertBtn.Enabled := (Table1.State = dsBrowse);</p>
<p>CancelBtn.Enabled := Table1.State in [dsInsert,dsEdit,dsSetKey]</p>
<p>end;</p>
<p> </p>
<p>上面的代码中,当Table1处于浏览状态(Browse状态时),
用户是不能够向数据库表中插入新记录的,此时InsertBtn按钮将变灰暗即无效。当Table1不处于Browse状态时,InsertBtn按钮有效,用户是可以向表中插入新记录。同理,只有当Table1处于特入状态(Insert状态)或编辑状态(Edit状态)或查找状态(SetKey状态)时,CancelBtn按钮才有效,也即用户可以取消当前插入的记录、修改当前的记录以及查找到的结果等。</p>
<p> </p>
<p align="center">15.6 字段部件和字段编辑器的使用</p>
<p> </p>
<p>字段部件有时又称字段对象它对应着数据库表中的列即字段,字段对象是不可见的部件,在Delphi中有两种方式创建字段部件:</p>
<p>①在应用程序运行过程中,随着数据集部件被激活,对应于数据库表中每一列的字段部件便动态地被创建。</p>
<p>②在设计过程中,程序设计人员利用字段编辑器(Fields Editor)可以创建永久性的字段部件,即使字段对象对应的数据库表的结构发生了变化时,这些字段部件也不会发生变化。</p>
<p>既然字段部件是对应于数据库表中的各个字段的,而数据库表中的字段有多种数据类型,所以字段部件相应也有多种类型,字段部件的类型与数据库表中的字段的数据类型的对应关系如表15.5所示。</p>
<p> </p>
<p>表15.5 字段部件的类型</p>
<p>━━━━━━━━━━━━━━━━━━━━━━━━━━━━</p>
<p>字段部件的类型 对应的数据类型</p>
<p>────────────────────────────</p>
<p>TStringField 字符串类型的字段</p>
<p>TSmallIntField 短整数类型的字段 -32768-32767</p>
<p>TIntegerField 整数类型的字段</p>
<p>TWordField 正整数类型的字段0-65535</p>
<p>TBooleanField 布尔型字段</p>
<p>TFloatField 浮点数类型的字段</p>
<p>TCurrenCyField 货币型字段</p>
<p>TDataField 日期型</p>
<p>TTimeField 时间型</p>
<p>TBCDField 小数位数固定的浮点数</p>
<p>TDataTimeField 日期时间型字段</p>
<p>━━━━━━━━━━━━━━━━━━━━━━━━━━━ </p>
<p>我们在本书中只介绍一些常见类型的字段部件的使用,其他类型字段部件的使用可以参看联机帮助文件。</p>
<p> </p>
<hr color="#EE9B73" size="1" width="94%">
</TD>
<TD CLASS="tt3" VALIGN="bottom" width="8%" background="bg.gif"><strong><A HREF="038.htm" ><FONT style="FONT-SIZE: 9pt">后一页</font></A><BR>
<A HREF="036.htm" ><FONT style="FONT-SIZE: 9pt">前一页</font></A><BR>
<A HREF="index.html" ><FONT style="FONT-SIZE: 9pt">回目录</font></A><BR>
<A HREF="../../../../../index.htm"><FONT style="FONT-SIZE: 9pt">回首页</font></A><BR>
</strong>
</TD>
</TR>
</table>
</BODY></HTML>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -