用户名: 密码: 验证码: gdcode 注册

在PB中如何实现数据模糊查询

时间:2007-06-15 来源: 作者: 【字体: 减小 增大点击: 收藏 | 投稿
  
代码及设计:

  1.新建一个窗口,命名为w_query。在窗口中放入一个数据窗口控件,命名为dw_master。在dw_master中放入一个数据窗口;放置一个按钮,命名为cb_query。见下图:





  2.新建一个结构(structure)命名为str_result_column,其参数如下:


  3.在dw_master增加两个用户事件,命名为ue_action_query、ue_action_refresh。 财.管家园.fs119.net

  4.在cb_query中增加如下代码:


  5.在窗口的Open事件中增加如下代码:

dw_master.setTransObject(sqlca)
  6.在dw_master的ue_action_query中增加如下代码:

str_result_columnlstr_1
//结构str_result_column的成员adw_result指查询结果所产生作用的dw
//成员adw_column指在本窗口查询条件所要显示的dw

lstr_1.adw_result=this
lstr_1.adw_column=this

OpenWithParm(wroot_dw_query,lstr_1)

财管家园 fs119.net

财管家园,fs119.net

财软联盟.fs119.net


财软联盟,fs119.net

财管家园,fs119.net

 7.在dw_master的ue_action_refresh事件中增加如下代码:

dw_master.retrieve()
  8.新建一个窗口,命名为wroot_dw_query,该窗口用以进行模糊查询。其设计完成后界面如下所示:


  其中"执行"按钮名为"cb_exec"、"返回"按钮名为"cb_exit"、"返回"按钮下的数据窗口名为dw_column,其dataObject为d_column_set、中间的数据窗口名为dw_where,其dataObject为d_where。

  9.d_column_set的设计完成界面如下所示:

财软联,盟,fs119.net


  10.其sql为:


  11.dw_where的设计完成界面如下:


  12.其sql为:

财软.联盟.fs119.net

财软联 盟 fs119.net

财软联盟.fs119.net


财管家,园,fs119.net

财软联盟.fs119.net

  13.属性和代码如下:

  1.wroot_dw_query属性:

X=9Y=1132Width=2912Height=712
Visible=trueEnabled=trueTitleBar=trueTitle="定位查询"
ControlMenu=trueBorder=trueWindowType=response!WindowState=normal!
BackColor=79741120
  2.窗口实例变量:

Booleanib_changed
LongMaxEditRow=1
StringsWhere,oldsql,orisql,is_title,is_section='WhereClause'
DataWindowdw_result,dw_detail
pfc_n_cst_stringinv_string
stringsSyntax
  注释:a.pfc_n_cst_string为PFC用户对象。

  3.窗口事件代码:

  3.1close事件:



  功能:将用户本次所输入的查询条件记录到文件sIniFile的WhereClause1...n小节中去以备下次启动时置初始查询条件。

财.软联盟.fs119.net



  3.2open事件:

  功能:设置初始值,具体请看代码中的注释。

integeri,row,li_where_row=10
stringtmp
str_result_columnlstr_1
//结构str_result_column的成员adw_result指查询结果所产生作用的dw
//成员adw_column指在本窗口查询条件所要显示的dw
lstr_1=Message.PowerObjectParm
dw_result=lstr_1.adw_result
dw_detail=lstr_1.adw_column
ifisnull(dw_result)ornotisvalid(dw_result)thenreturn
ifisnull(lstr_1.adw_column)ornotisvalid(lstr_1.adw_column)thenreturn

windowact_w
act_w=MainWindow.getactivesheet()
x=act_w.x8
y=act_w.yact_w.height-height258
width=act_w.width
cb_exec.x=width-cb_exec.width-80
cb_exit.x=width-cb_exec.width-80
dw_where.x=10
dw_where.Width=width-2*dw_where.X-cb_exec.width-100
//-----s
dw_column.visible=False
wf_setcolumn(lstr_1.adw_column,dw_column)
//orisql=dw_result.Object.DataWindow.Table.Select//原始语法,close中用.
财管.家园.fs119.net


orisql=dw_result.GetSqlSelect()//上句对CrossTab无效
oldsql=lower(orisql)
Fori=1toli_where_row
dw_where.InsertRow(0)
Next
dw_where.setrowfocusindicator(Hand!)
dw_where.ScrollToRow(0)
dw_where.SetColumn("column1")
cb_exec.SetFocus()
datawindowchilddwc
dw_where.GetChild("column1",dwc)
dwc.SetTransObject(sqlca)
dwc.Reset()
Fori=1todw_column.RowCount()
tmp=dw_column.GetItemString(i,1)
row=dwc.InsertRow(0)
dwc.SetItem(row,1,tmp)
Next
//将用户上次所输入的查询条件从文件sIniFile的WhereClause1...n小节中取出来,
//本次启动时置为初始查询条件.
windoww_parent
ifdw_result.GetParent().typeof()=window!then
w_parent=dw_result.GetParent()
is_title=w_parent.title
else
is_title=dw_result.DataObject
endif
ib_changed=True
row=0
tmp=''
is_title=gnv_app.is_regkey'\'is_title'\'scname
Fori=1toli_where_row
RegistryGet(is_title,is_sectionString(i),RegString!,tmp)
//tmp=ProfileString(sinifile,is_title,"WhereClause"string(i),"")
财管家园,fs119.net

iftmp<>""and(NotIsNull(tmp))then
//SetProfileString(sinifile,is_title,"WhereClause"string(i),"")
RegistrySet(is_title,is_sectionString(i),RegString!,'')
row
dw_where.object.data[row,1]=inv_string.of_gettoken(tmp,",")
dw_where.object.data[row,2]=inv_string.of_gettoken(tmp,",")
dw_where.object.data[row,3]=inv_string.of_gettoken(tmp,",")
dw_where.object.data[row,4]=inv_string.of_gettoken(tmp,",")
dw_where.object.data[row,5]=inv_string.of_gettoken(tmp,",")
dw_where.object.data[row,6]=inv_string.of_gettoken(tmp,",")
endif
Next
MaxEditRow=row//MaxEditRow为dw_where中当前已编辑过的最大行的行号.实例变量.
IfMaxEditRow=0ThenMaxEditRow=1
财管家园.fs119.net

财管家,园,fs119.net

财软,联盟,fs119.net


财管家 园 fs119.net

财管家.园.fs119.net

  4.函数:

  4.1publicfunctionstringwf_getywname(stringhzname)函数

  功能:返回"表名.列名",如"department.d_id"。


  4.2publicfunctionstringwf_getywtype(stringhzname)函数

  功能:返回列类型。


  注释:

  (1)f_getoken()函数代码如下:

财管家 园 fs119.net
  4.3publicfunctionstringwf_dateconvert(stringsvalue)函数

  功能:见程序中注释。

stringsyear,smonth,sday
dateidate
idate=date(svalue)
syear=string(year(idate))
smonth=string(month(idate))
sday=string(day(idate))
svalue=syear"-"smonth"-"sday
returnsvalue
endfunction
publicfunctionstringwf_datetime(stringinputvalue)
inputvalue=trim(inputvalue)
integerposition
stringbef,aft
/*bef为日期,aft为时间*/
position=pos(inputvalue,"")
ifposition=0theninputvalue="00:00:00"
position=pos(inputvalue,"")
ifposition=0then
return"error"
else
bef=left(inputvalue,position-1)
aft=right(inputvalue,len(inputvalue)-position)
if(notisdate(bef))or(notistime(aft))then
return"error"
endif
endif
//bef=wf_dateconvert(bef)
//returnbef""aft
stringsyear,smonth,sday
dateidate
idate=date(bef)
syear=string(year(idate))
smonth=right('00'string(month(idate)),2)

财软联盟,fs119.net

sday=right('00'string(day(idate)),2)
returnsyearsmonthsday
endfunction
publicsubroutinewf_setcolumn(datawindowdw_1,datawindowdw_2)
pfc_n_cst_stringlnv_string
Stringscol,stable_col
Stringshz,syw,stype,stable
Integeri,row
IfNotIsValid(dw_1)ThenReturn
IfNotIsValid(dw_2)ThenReturn
dw_2.ReSet()
Fori=1Tolong(dw_1.Object.DataWindow.Column.Count)
scol=dw_1.Describe("#"String(i)".Name")//列名(可变)
stable_col=dw_1.Describe(scol".dbName")//所在表.列名(OK)
stable=lnv_string.of_gettoken(stable_col,".")//所在表
syw=stable_col//列名(不变.OK)
shz=trim(dw_1.Describe(scol"_t.Text"))//中文名
stype=dw_1.Describe(scol".ColType")//列类型
ifdw_1.Describe(scol".Type")="column"&
andshz<>"!"andshz<>"?"then
shz=lnv_string.of_globalreplace(shz,"'","")//去掉单引号
shz=lnv_string.of_globalreplace(shz,'"','')//去掉双引号
shz=lnv_string.of_globalreplace(shz,"~r~n","_")//去掉换行符
shz=lnv_string.of_globalreplace(shz,"","_")//去掉空格
财软联.盟.fs119.net

shz=lnv_string.of_globalreplace(shz,":","")//去掉冒号
shz=lnv_string.of_globalreplace(shz,":","")//去掉冒号
row=dw_2.InsertRow(0)
dw_2.object.data[row,1]=shz
dw_2.object.data[row,2]=syw
dw_2.object.data[row,3]=stype
dw_2.object.data[row,4]=stable
endif
Next
财软,联盟,fs119.net

财软联,盟,fs119.net

财管家园.fs119.net


财管家 园 fs119.net

财 管家园 fs119.net

  4.4publicfunctionlongwf_min(longa,longb,longc)函数

  功能:给定三个数a,b,c,如果a,b,c均为0,则返回0;否则,返回a,b,c中不为0的数中的最小值.例1:a=0,b=0,c=0,则返回0。例2:a=0,b=2,c=6,则返回2。例3:a=9,b=0,c=0,则返回9。


  5.StaticText:st_1属性:

X=46Y=32Width=466Height=64
TabOrder=0Visible=trueText="请输入查询条件:"TextColor=0
BackColor=80269524Alignment=left!FillPattern=solid!
  6.CommandButton:cb_exit属性:

X=2578Y=376Width=256Height=108
TabOrder=30Visible=trueEnabled=trueText="&F.返回"

财管,家园,fs119.net

Cancel=true
  6.1CommandButton:cb_exit的clicked事件:

  功能:直接退出。

Close(parent)
  7.CommandButton:cb_exec属性:

X=2578Y=204Width=256Height=108
TabOrder=20Visible=trueEnabled=trueText="&Z.执行"
Default=true
  7.1CommandButton:cb_exec的clicked事件:

  功能:设置组和sql语法。


  注释:

  (1).n_cst_sql、n_cst_sqlattrib为PFC中用户对象,这里不再详述。

  8.DataWindow:dw_column属性: 财 管家园 fs119.net

X=2578Y=536Width=69Height=60
TabOrder=10Visible=trueEnabled=trueDataObject="d_column_set"
Border=trueLiveScroll=trueBorderStyle=stylebox 财软联,盟,fs119.net

财软联,盟,fs119.net

财管家 园 fs119.net


财软联 盟 fs119.net

财软.联盟.fs119.net

  9.DataWindow:dw_where属性:

X=46Y=120Width=2459Height=448
TabOrder=40Visible=trueEnabled=trueDataObject="d_where"
VScrollBar=trueBorder=trueBorderStyle=stylelowered!
  9.1DataWindow:dw_where的editchanged事件:

  功能:设置"执行"按钮是否有效。


  9.2DataWindow:dw_where的itemchanged事件:

  功能:见代码中的注释。

stringcolname,colvalue,logvalue
longcurrow
ib_changed=true
cb_exec.Enabled=True
currow=GetRow()
IfMaxEditRow<CurrowThenMaxEditRow=currow
//MaxEditRow为当前已编辑过的最大行的行号。实例变量。

财软,联盟,fs119.net

colname=GetColumnName()
colvalue=GetItemString(currow,colname)
ChooseCasedwo.name
Case'dispvalue'
Object.value[row]=data
CaseElse
EndChoose
//设置当前行的operator的初始值为"="
//设置上一行的logical的初始值为"and"
ifcolname="column1"then
ifcolvalue=""orisnull(colvalue)then
SetItem(currow,"operator","=")
ifcurrow>=2then
colvalue=GetItemString(currow-1,colname)
logvalue=GetItemString(currow-1,"logical")
ifcolvalue<>""and(logvalue=""orisnull(logvalue))then
SetItem(currow-1,"logical","and")
endif
endif
endif
endif
//检查并设置左括号。
longll,i
colvalue=GetText()
ifcolname="precol"then
ifcolvalue<>""andnotisnull(colvalue)then
ll=len(colvalue)
colvalue=""
Fori=1toll
colvalue="("
Next
SetItem(currow,"precol",colvalue)
this.Settext(colvalue)
Return2
endif
endif
  9.3DataWindow:dw_where的losefocus事件:

AcceptText()
财管家园,fs119.net

  9.4DataWindow:dw_where的rbuttondown事件:

  功能:设置弹出式菜单。


  注释:

  (1)m_cpq_rbutton_paste菜单的属性和代码如下:

1.MenuItem=m_1"a1"
Visible=trueEnabled=true

2.MenuItemsform_1
MenuItem=m_value"&V.取现有值"
Visible=trueEnabled=true

3.Scriptfor:ntclickedevent

longll_pos
StringsSyntax,ls_parm,ls_data,ls_disp
datawindowdwp
dwp=Message.PowerObjectParm
sSyntax=Message.StringParm
ifsSyntax=""orisNull(sSyntax)then
beep(3)
return
endif
OpenWithParm(w_paste,sSyntax)//w_paste为响应式窗口
ls_parm=Message.StringParm

财管家 园 fs119.net


ifls_parm<>"cancel"then
ll_pos=Pos(ls_parm,'/')
Ifll_pos=0Then
ls_data=ls_parm
ls_disp=ls_parm
Else
ls_data=Left(ls_parm,ll_pos-1)
ls_disp=Mid(ls_parm,ll_pos1)
EndIf
dwp.SetItem(dwp.GetRow(),"value",ls_data)
dwp.SetItem(dwp.GetRow(),"dispvalue",ls_disp)
dwp.AcceptText()
endif

5.MenuItem=m_clear"&D.清除本列"
Visible=trueEnabled=true

6.Scriptfor:clickedevent

datawindowdwp
dwp=Message.PowerObjectParm
dwp.DeleteRow(0)
dwp.InsertRow(0)
EndofScript
MenuItem=m_return"&N.返回"
Visible=trueEnabled=true 财软联 盟 fs119.net

财管家.园.fs119.net

财软.联盟.fs119.net


财管.家园.fs119.net

财管家园 fs119.net

  9.5DataWindow:dw_where的ue_where事件

  功能:形成WHERE子句,并更新语法框。

stringhzcol,ywcol,sValue,sType//,sWhere
//sWhere现为实例变量,在wroot_query中为局部变量.
stringsOper,sLog,sLeft_kh,sRight_kh,tmpsValue
longleft_kh,right_kh//左、右括号数
integeri,rownum,delnum//,typenum
dwItemStatusl_status
ifib_changed=truethen
ib_changed=false
else
return0
endif
rownum=dw_where.RowCount()
//去掉dw_where中MaxEditRow行以前所有中间为空或
//者输入不完整的行,并更新MaxEditRow.
i=1
delnum=0
DOWHILEi<=MaxEditRow
l_status=dw_where.GetItemStatus(i,0,Primary!)
ifl_status<>New!then
hzcol=GetItemString(i,"column1")
sValue=GetItemString(i,"value")
if(hzcol=""orisnull(hzcol))or(sValue=""orisnull(sValue))then
dw_where.DeleteRow(i)
delnum=1
MaxEditRow=-1
Continue
endif
else
dw_where.DeleteRow(i)

财管家园 fs119.net

delnum=1
MaxEditRow=-1
Continue
endif
i=1
LOOP
Fori=1toDelNum
dw_where.InsertRow(0)
Next
//检查左右括号是否匹配,即其数量是否一样多.
Fori=1toMaxEditRow
l_status=dw_where.GetItemStatus(i,0,Primary!)
ifl_status<>New!then
left_kh=inv_string.of_countoccurrences(GetItemString(i,"precol"),"(")
right_kh=inv_string.of_countoccurrences(GetItemString(i,"value"),")")
endif
Next
i=left_kh-right_kh
ifi<>0then
ifi>0then
sValue="查询条件中左括号比右括号多了"String(i)"个"
else
sValue="查询条件中左括号比右括号少了"String(-i)"个"
endif
ifMessageBox("综合查询输入错误",sValue",请改正;"&
"~r~n~r~n否则,所有查询条件将被忽略。",None!,OKCancel!,2)=1then
return1
else
dw_where.setfocus()
return0
endif
endif
//形成WHERE子句,并更新语法框。
sWhere=""
Fori=1toMaxEditRow
hzcol=GetItemString(i,"column1")
sOper=space(1)GetItemString(i,"operator")space(1)
财管家 园 fs119.net

//去掉空格键
sValue=Trim(GetItemString(i,"value"))
sLeft_kh=GetItemString(i,"precol")//保存左括号
ifisNull(sLeft_kh)thensLeft_kh=""
ifPos(sValue,")",1)>0then//保存右括号
sRight_kh=Right(sValue,(Len(sValue)-Pos(sValue,")",1)1))
else
sRight_kh=""
endif
sValue=inv_string.of_globalreplace(sValue,"'","")//去掉sValue中的单引号.
sValue=inv_string.of_globalreplace(sValue,'"','')//去掉sValue中的双引号.
sValue=inv_string.of_globalreplace(sValue,")","")//去掉sValue中的右括号.
sLog=GetItemString(i,"logical")
ifsLog=""orisNull(sLog)then
sLog="and"
dw_where.SetItem(i,"logical","and")
endif
ywcol=wf_getYwName(hzcol)//表名.列名
sType=lower(wf_getYwType(hzcol))
CHOOSECASEsType
CASE"char","character","string","nchar","nvarchar","varchar","time"
iftrim(sOper)="like"ortrim(sOper)="notlike"then
sWhere="("sLeft_khywcolsOper"'%"sValue"%')"sRight_khsLog
else
sWhere="("sLeft_khywcolsOper"'"sValue"')"sRight_khsLog
endif

财软.联盟.fs119.net


CASE"numeric","decimal","decimaln","dec","double","integer","int","smallint",&
"number","long","real","uint","ulong","unsignedint","unsignedinteger","unsignedlong"
iftrim(sOper)="like"ortrim(sOper)="notlike"then
ifMessageBox("提示信息",hzcol"不是字符型,不能使用<含有>或<不含有>操作符,"&
"~r~n~r~n请改正;否则,所有查询条件将被忽略。",None!,OKCancel!,2)=1then
return1
else
dw_where.setfocus()
return0
endif
endif
ifisNumber(sValue)then
sWhere="("sLeft_khywcolsOpersValue")"sRight_khsLog
else
ifMessageBox("综合查询输入错误",hzcol"的值应为数字型,请改正;"&
"~r~n~r~n否则,所有查询条件将被忽略。",None!,OKCancel!,2)=1then
Return1
else
dw_where.setfocus()
return0
endif
endif
CASE"date","datetime","datetimn","smalldatetime","timestamp"
iftrim(sOper)="like"ortrim(sOper)="notlike"then
ifMessageBox("提示信息",hzcol"不是字符型,不能使用<含有>或<不含有>操作符,"& 财软联盟 fs119.net
"~r~n~r~n请改正;否则,所有查询条件将被忽略。",None!,OKCancel!,2)=1then
return1
else
dw_where.setfocus()
return0
endif
endif
ifsType="date"then
ifnotisdate(sValue)then
ifMessageBox("综合查询输入错误",hzcol"的值应为日期型,请改正;"&
"~r~n~r~n否则,所有查询条件将被忽略.",None!,OKCancel!,2)=1then
Return1
else
dw_where.setfocus()
return0
endif
endif
sValue=wf_dateconvert(sValue)
sWhere="("sLeft_khywcolsOper"'"sValue"')"sRight_khsLog
else
//datetime型的字段在sybase中转换为字符串的类型
sValue=wf_datetime(sValue)
ifsValue="error"then
ifMessageBox("综合查询输入错误",hzcol"的值应为日期时间型,请改正;"&
"~r~n~r~n否则,所有查询条件将被忽略。",None!,OKCancel!,2)=1then
Return1
else
dw_where.setfocus()
return0
endif
endif
sWhere="("sLeft_kh"convert(varchar(8),"ywcol",112)"sOper"'"sValue"')"sRight_kh
sLog
endif
CASEELSE
beep(1) 财软.联盟.fs119.net
MessageBox("综合查询",sType"这个数据类型未在本模块中定义。")
Return0
ENDCHOOSE
Next
//去掉最后一个逻辑符。
Longpok,pp
pp=0
DOWHILETrue
pok=pp
pp=Pos(sWhere,")",pp1)
ifpp=0thenExit
LOOP
ifpok>0thensWhere=Trim(Left(sWhere,pok))
return1
//最后一个逻辑符去掉结束.
//至此,用户的WHERE语句部分已经形成完毕于sWhere中.
  9.6DataWindow:dw_where的ue_mousemove事件

  功能:控制鼠标的移动。

strings_object
s_object=This.GetObjectAtPointer()
ifleft(s_object,5)="value"then
MainWindow.SetMicroHelp("此时按鼠标右键可粘贴现有值")
else
MainWindow.SetMicroHelp("准备好")
endif
  9.7DataWindow:dw_where的ue_retrieve事件

  功能:对数据窗口进行查询,详细请见代码。

//如果数据窗口dw_result上并无ue_action_refresh事件,
财 软联盟 fs119.net

//则用户必须重载本事件,编写自己的脚本.
//如:
//dw_result.retrieve()
//
//或者如果数据窗口dw_result有retrieve参数,
//则用户也必须重载本事件,编写自己的脚本.
//如:
//stringls_id
//ls_id=...
//dw_result.retrieve(ls_id)
dw_result.triggerevent("ue_action_refresh") 财软.联盟.fs119.net

财管,家园,fs119.net

财软联 盟 fs119.net


文章摘自网络,如有侵权,请与我们联系.
数据统计中!!
上一篇:PB中用WindowsAPI制作位图菜单
下一篇:在PB7.0中实现多数据窗口的连续打印

精品课程推荐



用户名: 密码: 匿名? 注册