2008年12月31日星期三

宝成各區通讯方式




陽新寶加鞋廠(湖北黃石)

湖北黃石-陽新寶加鞋廠(171)內線分機已於近日開通,
該區分機號碼如附檔;各區撥法如下:

8 + 171 + 分機號碼

2008年12月30日星期二

倍力資訊

http://www.mpinfo.com.tw/Marketing/article.asp?Menu_Page=專欄文章

PB程序之间是怎样传递字符串变量?

我们知道可以用Send ( handle, message#, lowword, long )函数完成不同程序窗口间的消息传递,其中最后两个参数为long型,因此可以利用这两个参数来传递数字型的变量。如果想传递的是字符串呢?由于每个进程都有自己独立的内存地址和内存空间,因此不可能直接通过访问变量地址的方法得到变量。
下面给出pb的方法:
 source程序:
  外部函数:
  Function ulong GetCurrentProcessId() LIBRARY "kernel32.dll"  Function integer SndMsg(long hWnd, long uMsg, long url, &  ref blob info) library "user32.dll" Alias For "SendMessageA constant long PBM_CUSTOM01 = 1024  
程序:  
IF il_hTarget <= 0 THEN findTarget() //找接受变量的窗口,主要用findwindow实现
  IF il_hTarget > 0 THEN
  String ls_len
  //组成一个要发送的字符串
  url+= " "+info+" "+String(srctype)+" "+String(offlinetype)
  //计算整个要发送字符的长度,并转化为长度为10的字符串
  ls_len = String(Len(url))
  IF Len(ls_len) < 10 THEN
  ls_len = Space(10 - Len(ls_len))+ls_len
  END IF
  //转化为blob并发送
  Blob lb_snd
  lb_snd = Blob(ls_len+url)
  SndMsg(il_hTarget, PBM_CUSTOM01 +9,getcurrentprocessID(),lb_snd)
  END IF
  target程序:
  外部函数:
  Function ulong OpenProcess(ulong dwDesiredAccess,ulong bInheritHandle,ulong dwProcessId) LIBRARY "kernel32.dll"
  Function ulong ReadProcessMemoryStr(ulong hProcess,long lpBaseAddress,ref string lpBuffer,ulong nSize,ref long lpNumberOfBytesWritten) LIBRARY "kernel32.dll" Alias for "ReadProcessMemory"
  Function ulong ReadProcessMemoryBlob(ulong hProcess,long lpBaseAddress,ref blob lpBuffer,ulong nSize,ref long lpNumberOfBytesWritten) LIBRARY "kernel32.dll" Alias for "ReadProcessMemory"
  事件pbm_custom10:
  If (wparam = 0) Or (lparam = 0) THEN RETURN
  Long ll_null
  SetNull(ll_null)
  Long processhnd
  CONSTANT Long PROCESS_VM_READ = 16
    processhnd = openprocess(PROCESS_VM_READ,0,wparam);
  //读取发送进程的内存数据
  String ls_size
  Long ll_size

层次查询

层次查询(connect by查询)
它的语法是:
SELECT *
FROM 
WHERE
START WITH 
CONNECT BY 
ORDER BY col1, col2 ...
其中,start with 表示的是根刻录行,connect by 指定了父记录行和子记录行之间的关系,在层次查询中,条件表达式必须使用prior操作符来指定父记录行,如:
... PRIOR expr = expr
or
... expr = PRIOR expr 
如果connect by 条件是一个组合条件,那么只有一个条件需要prior操作符,如:CONNECT BY last_name != 'King' AND PRIOR employee_id = manager_id不过,connect by 不能包含子查询。
prior是一个二元操作符,最常见的是用于列值相等的比较,它让Oracle使用对应列的父亲行的值。使用非相等比较,极有可能倒致查询陷入无穷循环,以出错终止。
与join的组合, 
如果where子句有join操作,在执行connect by之前会先执行join  
如果where子句没有join操作,会在执行connect by之后再执行这些条件  
Oracle会执行下述步骤来完成connect by操作:
1. 执行条件过滤,取决于是否有join操作
2. 选择层次中满足start with条件的的根行,即层次树中第一层的节点行
3. 选择每个根行的子行,每个子行必须满足connect by条件中对应于根行的条件
4. 选择子行的后代,每次都使用子行与对应的父行进行connect by 匹配
5. 如果where中不含有join操作,那么Oracle将在执行完connect by操作之后移掉不符合条件的那么记录行。
当一行既是父行,也是子行时,就会产生死循环。例,找出雇员及经理之间的关系的结果: 
SELECT employee_id, last_name, manager_id
   FROM employees
   CONNECT BY PRIOR employee_id = manager_id;

EMPLOYEE_ID LAST_NAME                 MANAGER_ID
----------- ------------------------- ----------
        101 Kochhar                          100
        108 Greenberg                        101
        109 Faviet                           108
        110 Chen                             108
        111 Sciarra                          108
        112 Urman                            108
        113 Popp                             108
        200 Whalen                           101
 
举子例子说明,
对emp表,如果以条件“where mgr is NULL”开始,先会产生没有经理的那些行,以这些行作为根,开始搜索,再执行“CONNECT BY PRIOR EMPNO = MGR”,下面是这个查询的具体过程: 
Using EMP, the start with SET is:

scott@ORA8I.WORLD> select ename, empno, mgr from emp
  2  where mgr is null;

ENAME           EMPNO        MGR
---------- ---------- ----------
KING             7839

Now, if we do the "connect by manually" we would find:

scott@ORA8I.WORLD> select ename, empno, mgr
  2  from emp where mgr = 7839;

ENAME           EMPNO        MGR
---------- ---------- ----------
JONES            7566       7839
BLAKE            7698       7839
CLARK            7782       7839

scott@ORA8I.WORLD> 

KINGS empno is the prior empno.  If we build the entire hierarch -- we have:

scott@ORA8I.WORLD> select lpad(' ',level*2,' ')||ename ename, empno, mgr
  2  from emp
  3  START WITH MGR IS NULL
  4  CONNECT BY PRIOR EMPNO = MGR
  5  /

ENAME                EMPNO        MGR
--------------- ---------- ----------
  KING                7839
    JONES             7566       7839
      SCOTT           7788       7566
        ADAMS         7876       7788
      FORD            7902       7566
        SMITH         7369       7902
    BLAKE             7698       7839
      ALLEN           7499       7698
      WARD            7521       7698
      MARTIN          7654       7698
      TURNER          7844       7698
      JAMES           7900       7698
    CLARK             7782       7839
      MILLER          7934       7782

14 rows selected.

PB中自定義事件ID含義

PB中自定義事件ID含義
单选或多选按钮消息(前缀:pbm_bm)
pbm_bmgetcheck 单选按钮或多选按钮是否被选。
pbm_bmgetstate 按钮是否加亮。
pbm_bmsetcheck 将无线按钮或确认框的选中状态改为未选中状态,反之亦然。
pbm_bmsetstate 加亮或不加亮按钮。
pbm_bmchange 改变按钮的风格,例如,改为单选按钮或组合框。
单选或多选按钮通知消息(前缀:pbm_bn)
pbm_bnclicked 按钮控件被点中。
pbm_bndisable 使按钮控件无效。
pbm_bndoubleclicked 按钮控件被双点。
pbm_bndragdrop 一个对象被放到按钮控件。
pbm_bndragenter 一个对象被拖到按钮控件。
pbm_bndragleave 一个对象被拖离按钮控件。
pbm_bndragover 一个对象被拖经按钮控件。
pbm_bnhilite 按钮控件被加亮。
pbm_bnpaint 按钮控件被绘制。
pbm_bnsetfocus 按钮控件获得聚焦。
pbm_bnunhilite 按钮控件不被加亮。
通用对话框消息(前缀:pbm_cb)
pbm_cbaddstring 将字符串加到通用对话框。
pbm_cbdeletestring 从通用对话框删除一个字符串。
pbm_cbdir 加一个目录列表到通用对话框。
pbm_cbfindstring 搜索以一组字符开头的字符串。
pbm_cbfindstringexact 搜索与所提供的字符完全匹配的字符串。
pbm_cbgetcount 列表框中的项数。
pbm_cbgetcursel 当前被选项的数目。
pbm_cbgetdroppedcontrolset 列表框在屏幕上的坐标位置。
pbm_cbgeteditsel 编辑器控件中被选字符的范围。
pbm_cbgetextendedui 缺省或扩展的用户界面。
pbm_cbgetitemdata 重画的列表框中的4字节(32位)项。
pbm_cbgetitemheight 列表框中某一项的高度。
pbm_cbgetlbtext 列表框中的文本。
pbm_cbgetlbtextlen 列表框中文本的长度。
pbm_cbinsertstring 向列表框中增加新的字符串或4字节项。
pbm_cblimittext 限制能被输入到列表框中的字符数。
pbm_cbresetcontent 删除列表框中所有元素。
pbm_cbselectstring 搜索匹配的字符串并显示。
pbm_cbsetcursel 在列表框中选择并显示一项。
pbm_cbseteditsel 在列表框的编辑区域中选择一块文本。
pbm_cbsetextendedui 设置缺省或扩展的用户界面。
pbm_cbsetitemdata 在列表框中设定4字节(32位)项。
pbm_cbsetitemheight 设置列表框中项的高度。
pbm_cbshowdropdown 转换(显示或隐藏)列表框中拖放区域。
通用对话框通知消息(前缀:pbm_cbn)
pbm_cbndblclk 用户在列表中某一项上双点。
pbm_cbndragdrop 一个对象被放到通用对话框控件上。
pbm_cbndragenter 一个对象被拖到通用对话框控件上。
pbm_cbndragleave 一个对象被拖离通用对话框控件。
pbm_cbndragover 一个对象被拖经通用对话框控件。
pbm_cbndropdown 列表框的下放区域即将被显示。
pbm_cbneditchange 编辑器控件中的文本发生变化。
pbm_cbneditupdate 列表框编辑器控件中的文本即将被改变。
pbm_cbnerrspace 列表框满,不能再向其中加入项。
pbm_cbnkillfocus 通用列表框失去聚焦。
pbm_cbnselchange 列表框中被选文本被改变。
pbm_cbnselendcancel 用户按下了"取消"按钮。
pbm_cbnselendok 用户按下了"确认"按钮。
pbm_cbnsetfocus 通用对话控件拥有聚焦。
数据窗口消息(前缀:pbm_dw)
pbm_dwclosedropdown 关闭下拉式数据窗口。
pbm_dwscrollend 在数据窗口中卷滚到最后一行。
pbm_dwscrollhome 在数据窗口中卷滚到第一行。
pbm_dwscrolllineend 卷滚到当前行的行尾(水平方向)。
pbm_dwscrolllinehome 卷滚到当前行的行首(水平方向)。
数据窗口通知消息(前缀:pbm_dwn)
pbm_dwnbacktabout 即将通过Shift+Tab组合键离开该控件。
pbm_dwnchanging 控件即将被改变。
pbm_dwndropdown 下拉式列表框的下拉部分即将可见。
pbm_dwngraphcreate 即将创建图形。
pbm_dwnitemchangefocus 数据窗口控件中当前项的聚焦改变。
pbm_dwnitemvalidationerror 对当前项的修改引起了一个合法性检查错误。
pbm_dwnkey 有键被按下。使用KeyDown()处理键盘值。
pbm_dwnlbuttondown 鼠标左键被按下。
pbm_dwnlbuttonup 鼠标左键被松开。
pbm_dwnmbuttonclk 鼠标中键点击。
pbm_dwnmbuttondbclk 鼠标中键双击。
pbm_dwnmousemove 鼠标移动。
pbm_dwnprintmarginchange 打印边界被改变。
pbm_dwnprocessenter 回车键被按下。
pbm_dwnrowchange 数据窗口中聚焦从一行转向另一行。
pbm_dwntabdownout 用户在数据窗口最后一行按了下箭头键。
pbm_dwntabout 用户在数据窗口的最后一行/列中按了tab键。
pbm_dwntabupout 用户在数据窗口第一行中按了上箭头键。
动态数据交换(DDE)消息(前缀:pbm_dde)
pbm_ddeddeack 收到一个DDE消息。
pbm_ddeddeinitiate 开始一个DDE会话。
pbm_ddeddeterminate 终止一个DDE会话。
编辑器控件消息(前缀:pbm_em)
pbm_emcanundo 编辑器控件是否能撤消上一次修改。
pbm_ememptyundobuffer 清空由Windows管理的取消操作的缓冲区。
pbm_emfmtlines 在多行编辑器控件的行尾增加或删除回车换行。
pbm_emgetfirstvisibleline 返回编辑器控件中可见的第一行的行号。
pbm_emgethandle 获得编辑器控件使用的内存句柄。
pbm_emgetline 从编辑器控件中复制一行到内存中的一个缓冲区。
pbm_emgetlinecount 返回多行编辑器控件的行数。
pbm_emgetmodify 文本是否被用户修改。
pbm_emgetrect 返回控件的长方形域。
pbm_emgetsel 返回被选文本的起始位置。
pbm_emlimittext 限制用户键入的文本长度。
pbm_emlinefromchar 返回被选文本的行号。
pbm_emlineindex 返回编辑器控件中被选行第一个字符在编辑串中的位置。
pbm_emlinelength 返回编辑器控件中被选行中的字符数。
pbm_emlinescroll 水平或垂直卷滚编辑器控件。
pbm_emreplacesel 从剪贴板或从键盘上用新文本替换被选文本。
pbm_emsethandle 设置编辑器控件的句柄指向内存中的一个缓冲区。
pbm_emsetmodify 设置编辑器控件的modified标志。
pbm_emsetpasswordchar 设置用户输入任何文本时显示的字符,在输入密码时的显示。
pbm_emsetrect 设置/重置编辑器控件所在的长方形区域,编辑器控件中的文本被重画。
pbm_emsetrectnp 除了不重画文本,大致与setrect相同。
pbm_emsetsel 选择字符。
pbm_emsettabstops 在多行编辑器控件中设置tabstops。
pbm_emsetwordbreak 设置新的词拆分函数。
pbm_emsetwordbreakproc 设置新的词拆分过程。
pbm_emundo 撤消最近的编辑操作。
编辑控件通知消息(前缀:pbm_en)
pbm_enchange 编辑器控件中的文本发生改变。
pbm_enerrspace 编辑器控件内存缓冲区溢出。
pbm_enhscroll 用户点中上水平卷滚条。
pbm_enmaxtext 用户试图输入比允许更多的文本。
pbm_enupdate 编辑器控件即将显示用户的修改。
pbm_envscroll 用户点中了垂直卷滚条。
列表框消息(前缀:pbm_lb)
pbm_lbaddstring 向列表框控件中增加一项或一个字符串。
pbm_lbdeletestring 从列表框中删除一项或一个字符串。
pbm_lbdir 用目录列表填充列表框。
pbm_lbfindstring 在列表框中搜索与所给字符串部分匹配的第一项。
pbm_lbfindstringexact 在列表框中搜索与所给字符串精确匹配的第一项。
pbm_lbgetcaretindex 在列表框中搜索拥有聚焦的项。
pbm_lbgetcount 确定列表框中的项数。
pbm_lbgetcursel 确定所选项是第几项。
pbm_lbgethorizontalextent 获得列表框的宽度、计算水平卷滚。
pbm_lbgetitemheight 确定列表框控件中项的高度。
pbm_lbgetitemrect 确定列表框的尺寸。
pbm_lbgetsel 获得列表框中当前所选的项。
pbm_lbgetselcount 在多选列表框中获得所选项的数目。
pbm_lbgetselitems 用列表框中表框各自的项号填充一个给定的整数数组。
pbm_lbgettext 获得列表框中当前所选项的文本。
pbm_lbgettextlen 获得列表框中当前所选项的文本中的字符数。
pbm_lbgettopindex 确定列表框中可见的最上面一项的项号。
pbm_lbinsertstring 向列表框中加入一个新字符串。
pbm_lbresetcontent 重置(消除)列表框中的内容。
pbm_lbselectstring 搜索并加亮与所给字符匹配的字符串。
pbm_lbselitemrange 选择/取消列表框中某一范围中的项。
pbm_lbsetcaretindex 设置列表框中的某一项拥有聚焦。
pbm_lbsetcolumnwidth 设置列表框中列的宽度。
pbm_lbsetcursel 在列表框中选择并加亮一项;如果需要,卷滚到列表框。
pbm_lbsethorizontaltext 设置列表框中被水平卷滚的单元数。
pbm_lbsetitemdata 设置与列表框相关的32位/4字节值。
pbm_lbsetitemheight 设置列表框中项的高度。
pbm_lbsetsel 在列表框中选择一个字符串。
pbm_lbsettabstops 设置列表框控件中tabstops的位置。
pbm_lbsettopindex 卷滚列表框使特定的项成为可见的最上面一项。
列表框通知消息(前缀:pbm_en) 
pbm_endblclk 用户在列表框控件中的某一项上双击。
pbm_enerrspace 用户试图超越可在列表框中输入字符的最大限制。
pbm_enselcancel 当前选取文本被取消。
pbm_enselchange 用户在列表框中选择或取消了一项。
窗口消息(前缀:pbm_)
pbm_activateapp 被激活的窗口属于另外一个应用。
pbm_askcbformatname 要求剪贴板中的内容被复制到一个使用自定义格式的文本缓冲区中。
pbm_char 传送键盘上按下的键。
pbm_chartoitem 通过转换键盘来的字符,帮助列表框定位其中的项。
pbm_childactivate 一个子窗口被移动或激活。
pbm_clear 用户要删除当前编辑器控件中的内容。
pbm_command 用户选择了一个菜单项、控件,或使用了加速键。
pbm_compacting 系统内存资源不足;当Windows占用了多于1/8的CPU时间紧缩内存时,产生这条消息。
pbm_compareitem 当新的一项被加入列表框或组合框时产生此消息,Window用这条消息进行项之间的比较。
pbm_ctlcolor 一个控件即将被画出,可在此时改变控件的颜色。
pbm_deadchar 用户选择了一种非英语字符集或其它特殊字符集,这将改变下面将要输入的字符。
pbm_deleteitem 从列表框或通用对话框中移去一项。
pbm_destroyclipboard 剪贴板内容被清除。
pbm_devmodechanged WIN.INI中的一个设备名被修改。
pbm_drawclipboard 剪贴板内容发生改变。
pbm_drawitem 列表框或通用对话框的一项内容被改变。
pbm_dropfiles 当鼠标左键在一个注册为拖放文件接受器的应用上释放时,发出该消息。
pbm_erasebkgnd 窗口的客户区需要重画。
pbm_fontchange 应用可用的字体数改变。
pbm_getdlgcode 通知消息,说明当前使用哪种类型的键盘。
pbm_getfont 获取当前激活的字体。
pbm_getminmaxinto Windows正在检查最小化或最大化窗口的尺寸。
pbm_gettext 从一个控件(如按钮或编辑器控件)中复制文本到一个内存缓冲区。
pbm_gettextlength 用来确定一个控件中的字符数。
pbm_hscrollclipboard 剪贴板的水平卷滚条被使用。
pbm_iconerasebkgnd 一个最小化窗口需要重化背景。
pbm_initdialog 一个对话框即将被显示。
pbm_initmenu 一个菜单即将被显示。
pbm_initmenupopup 一个弹出式窗口即将被显示。
pbm_keydown 键盘上的一个键被按下。
pbm_keyup 键盘上的一个键被释放。
pbm_mdiactive 一个MDI子窗口(表单)被激活。
pbm_mdicascade 以重叠的形式重排所有的表单。
pbm_mdicreate 创建一个表单。
pbm_mdidestroy 从MDI框架中移去一个表单。
pbm_mdigetactive 获得当前活动的MDI表单的句柄。
pbm_mdiiconrange 在一个MDI框架中重排最小化表单的图标。
pbm_mdimaximize 最大化一个MDI子表单。
pbm_mdinext 激活下一个MDI表单(紧接着活动表单的表单)。
pbm_mdirestore 把MDI表单恢复到它原来的大小。
pbm_mdisetmenu 将一个菜单与一个MDI表单联系起来。
pbm_mdifitle 平铺所有的MDI表单。
pbm_measureitem 这个消息被送给即将创建的、内有按钮或其它控件的窗口。
pbm_menuchar 用户使用了一个快捷键,但系统不支持该快捷键。
pbm_menuselect 用户选择了一个菜单项。
pbm_mouseactivate 用户在一个非活动窗口中点击了鼠标。
pbm_mousemove 用户移动了鼠标。
pbm_ncactivate 窗口的非客户区即将被激活。
pbm_nccalcsize 窗口的尺寸需要重新计算。
pbm_nccreate 窗口即将创建它的非客户区。
pbm_ncdestroy 窗口的非共享区被析构。
pbm_nchittest 每次非客户区被移动时都发送该消息。
pbm_nclbuttondblclk 用户在非客户区双点了鼠标左键。
pbm_ncpaint 非客户需要画出。
pbm_nextdlgctl 在对话框中将聚焦转给另一个控件。
pbm_paint 窗口的客户区需要被画出。
pbm_paintclipboard 剪贴板应用有剪贴操作,剪贴板查看器需重画。
pbm_palettechanged 系统调色板被改变。
pbm_paletteischanging 系统调色板即将被改变。
pbm_parentnotify 通知父窗口一个子窗口即将被创建。
pbm_querydragicon 用户要拖一个最小化窗口。
pbm_queryendsession 通知消息,说明窗口即将被关闭。
pbm_querynewpalette 应用即将收到输入聚焦,应该执行必要的颜色调整。
pbm_queryopen 一个最小化窗口即将被恢复。
pbm_quit 应用处理的最后一个消息。
pbm_renderallformats 通知一个剪贴板格式的拥有者,应用将失去所有的格式。
pbm_renderformats 通知消息,说明放在剪贴板中的数据应该用一种特殊格式传送。
pbm_setcursor 通知消息,说明鼠标指针在一个窗口中移动。
pbm_setfont 用来在对话框中改变字体。
pbm_setredraw 在加一个新项之前发送给列表框或通用对话框。
pbm_settext 用来改变窗口的标题或文本。
pbm_sizeclipboard 剪贴板查看器应用改变尺寸。
pbm_spoolerstatus 一个打印管理器任务被添加或删除。
pbm_syschar 键和其它某键同时被按下。
pbm_syscolorchange 一种或多种系统颜色被改变。
pbm_syscommand 用户选择了一个系统菜单命令。
pbm_sysdeadchar 通知消息,说明一种非英语字符集被选定。
pbm_syskeydown 用户按下某键的同时按下了键。
pbm_syskeyup 用户释放了组合键。
pbm_timechange 系统时钟被修改。
pbm_undo 从undo缓冲区复制文本到编辑器控件。
pbm_vkeytoitem 当一个列表框拥有聚焦时,用户按下了一个键。
pbm_vscroll 用户点击了垂直卷滚条。
pbm_vscrollclipboard 剪贴板查看器的垂直卷滚条被点击。
pbm_windowposchanged 窗口位置发生改变。
pbm_windowposchanging 窗口位置即将发生改变。
pbm_wininichange WIN.INI文件被修改。

重置sequence值

create or replace procedure resetsequence
--重置sequence值
--declare
/*
Description : 重新reset序列號
每天由00:01由OS排程 /home/oracle/batch/job_dq_matin.sh 自動執行
Modify_Date: 2008/12/01

*/
is
i number(10);
J number(10);
tsql varchar2(100);
Jtsql varchar2(100);
begin
select Y3_APPCHECK.nextval into i from dual;
i:=-(i-1);
tsql:='alter sequence Y3_APPCHECK increment by'|| i;
execute immediate tsql;
select Y3_APPCHECK.nextval into i from dual;
tsql:='alter sequence Y3_APPCHECK increment by 1';
execute immediate tsql;

select Y3_GWIN.nextval into J from dual;
J:=-(J-1);
Jtsql:='alter sequence Y3_GWIN increment by'|| J;
execute immediate Jtsql;
select Y3_GWIN.nextval into J from dual;
Jtsql:='alter sequence Y3_GWIN increment by 1';
execute immediate Jtsql;
end;

2008年12月29日星期一

也谈“PB中相关联下拉数据窗口的实现”(jqz1225原创)

“PB中相关联下拉数据窗口的实现”中的原文:许多资料称设置检索参数是最简单、最方便的有效解决方法,也提出了几种隐藏系统自动弹出的“Specify Retrieval”对话框的方法。但令人遗憾的是本人竭尽所能也未能如愿(主要是无法隐藏系统自动弹出的“Specify Retrieval”对话框)。

看了之后,觉得怎么可能,我是个pb的初学者,但我也不相信无法隐藏统自动弹出的“Specify Retrieval”对话框,于是用原文章的三张表试了试。

一、建立datawindow

1) d_dept:

SELECT "dept"."dept_id", "dept"."dept_name" FROM "dept"

2) d_unit:

SELECT "unit"."unit_id",
"unit"."unit_name",
"unit"."dept_id"
FROM "unit"
WHERE "unit"."dept_id" = :as_dept_id
此数据窗口使用了retrieval argument: "as_dept_id"


3) d_feedata:

SELECT "feedata"."dept_id",
"feedata"."unit_id",
"feedata"."num"
FROM "feedata"

此数据窗口的

dept_id字段:Edit Style: Dropdown datawindow, 对应的datawindow为d_dept

unit_id字段:Edit Style: Dropdown datawindow, 对应的datawindow为d_unit, 其AutoRetrieve设为False

二、建立窗口w_main

1. w_main的open事件:

datawindowchild child_dept, child_unit

dw_1.settransobject(sqlca)
dw_1.retrieve()
//
if dw_1.getchild( ''''dept_id'''', child_dept)<0 then
messagebox(''''警告'''',''''数据字典有误'''')
close(this)
return
end if

child_dept.settransobject(sqlca)
child_dept.retrieve()
//
if dw_1.getchild( ''''unit_id'''', child_unit)<0 then
messagebox(''''警告'''',''''数据字典有误'''')
close(this)
return
end if

child_unit.settransobject(sqlca)

// child_unit.retrieve() //此句不能写,否则retrieval argument窗口就出来了

2. dw_1的itemchanged事件:

datawindowchild child_unit

if dwo.name = ''''dept_id'''' then //dept_id字段的值发生改变
if dw_1.getchild( ''''unit_id'''', child_unit)< 0 then
messagebox(''''警告'''',''''数据字典有误'''')
return
end if
child_unit.retrieve(data) // data即为dept_id当前的值,此时才带参数值调用retrieve
end if


三、结论

上文中用黑体标出的三个地方是关键。

来源转载: http://www.host01.com/article/software/PowerBuilder/20060918005202866.htm

PB学习笔记之SQL语句

任何对sql类数据库操作的语言必学的:),下面的是PB版本,有一些PB的特性.

SQL语句
sql语句以;结束,可写成多行形式而不用&
1、SELECT
注意:变量前加:
一个例子:
SELECT Employee.Emp_id,Employee.Emp_name,
Employee.Emp_salary,Dept.Dept_name
FROM Employee,Dept
WHERE (Emp_name like ''''张%'''')AND (Emp_sex=''''男'''')
AND Employee.Dept_id=Dept.Dept_id
ORDER BY Employee.Emp_id;

给变量的例子:
Dec Emp_salary
SELECT max(Emp_salary)
INTO :Emp_salary
FROM Employee;


2、INSERT
一个例子:
Int Emp_nbr
String Emp_name
Emp_nbr=Integer(sle_number.Text)
Emp_name=sle_name.Text
INSERT INTO Employee(employee.Emp_nbr,employee.Emp_name)
 VALUES(:Emp_nbr,:Emp_name)
USING Emp_tran;

3、UPDATE
一个例子:
UPDATE Employee//表名
SET emp_name=:sle_Name.Text //修改
 WHERE Employee.emp_nbr=:Emp_nbr;//修改条件

4、DELETE
一个例子:
DELETE FROM Employee //从表Employee
 WHERE Emp_nbr <100;删除条件满足的记录
5、CONNECT和DISCONNECT
执行DISCONNECT前自动执行COMMIT
6、COMMIT和ROLLBACK
7、使用游标(用来保存多条记录操作)
DECLARE,OPEN,FECTH...INTO...:NAME,CLOSE,DELETE(删除游标指向的记录),UPDATE(修改游标指向的记录)
利用游标打开多个记录的例子
//声明powerscript变量,存放读出的雇员姓名
String emp_cur CURSOR FOR
 SELECT emp_name FROM EMPLOYEE
 WHERE emp_state=:sle_1.text;
//打开游标,执行SELECT语句
OPEN emp_cur;
//从结果集中取第一条记录
FETCH emp_cur INTO "emp_name_var;
//判断FETCH语句执行情况
IF SQLCA.SQLCode<0 THEN
 MessageBox("Datebase Error",&//显示错误信息
 SQLCA.SQLErrText,Exclamation!)
RETURN
END IF
//如果FETCH语句执行正确,用循环语句逐条取结果集中的记录,到取完
DO WHILE SQLCA.SQLCode=0 //是否取完数据
//把取出的雇员姓名加入下拉列表框中
dlbl_1.additem(emp_name_var)
//继续从结果集中取下一符合条件的数据
FETCH emp_cur INTO :emp_name_var;
LOOP
//关闭游标
CLOSE emp_cur;

8、处理BLOB型数据(大部分语句只能对一条记录进行操作,多余则出错)
SELECTBLOB,

一个例子:
//声明BLOB型变量Emp_id_pic,用语存放Emp_pic列的数据
Blob Emp_pic
SELECTBLOB Emp_pic
 INTO :Emp_id_pic
 FROM Employee
 WHERE Employee.Emp_Id="001"
 USING Emp_tran;
//如果执行正确,在pb_1中显示照片
IF Emp_tran.SQLCode=0 THEN
pb1.SetPicture(Emp_id_pic)
END IF

UPDATEBLOB
一个例子:
Integer fh
Blob Emp_id_pic
//以读方式打开一个流模式文件
fh=FileOpen("c:\emp_100.bmp",StreamMode!)
//判断打开文件是否成功
IF fh<>-1 THEN
//从文件中读取图形数据存于Blob型变量
 FileRead(fh,emp_id_pic)
//关闭文件
 FileClose(fh)
//修改表的emp_pic列
UPDATEBLOB Employee
SET emp_pic=:Emp_id_pic
 WHERE EMp-Id="001";
END IF
IF SQLCA.SQLNRows>0 THEN//判断是否返回结果
 COMMIT;/提交事务
ELSE
ROLLBACK;//回滚事务
END IF

9、动态SQL语句
事务对象,动态描述区(SQLSA),动态描述区(SQLCA)
示例1:
String Mysql
Mysql ="CREAT TABLE Employee"&
 +"(emp_id char(6)not null,"&
 +"emp_hbr integer not null,"&
 +"dept_id integer not null,"&
 +"emp_fname char(10) not null,"&
 +"emp_lname char(20) not null)"
EXCUTE IMMEDIATE :Mysql;
实例2:
EXCUTE IMMEDIATE "DROP TABLE Employee" USING My_trans;
等价于:
String Mysql
Mysql+"DROP TABLE Employee"
EXCUTE IMMEDIATE :Mysql USING My_trans

实例3:
//在表中插入记录
Int Dept_id_var=156
String Dept_name_var
SetNull(Dept_name_var)
CONNECT;//
PREPARE SQLCA //prepare的作用???
 FROM "INSERT INTO dept VALUES(?,?)";
EXCUTE SQLCA USING :Dept_id_var,:Dept_name_var;

來源: http://www.host01.com/article/software/PowerBuilder/20060918005202286.htm

DataWindow Processing

Processing DataWindow object property
Description

The type of processing required to display the data in the selected presentation style.

Controls

DataWindows

Syntax

PowerBuilder dot notation:

dw_control.Object.DataWindow.Processing

Describe argument:

"DataWindow.Processing"

Return values are:

0 — (Default) Form, group, n-up, or tabular
1 — Grid
2 — Label
3 — Graph
4 — Crosstab
5 — Composite
6 — OLE
7 — RichText

2008年12月27日星期六

oracle 论坛汇集:

http://www.cnoug.org/index.php id:cyh0769

99乘法表

正反99表显示:
SELECT R1 || '*' || R1 || '=' || R1 * R1 A,
DECODE(R2, '', '', R2 || '*' || R1 || '=' || R2 * R1) B,
DECODE(R3, '', '', R3 || '*' || R1 || '=' || R3 * R1) C,
DECODE(R4, '', '', R4 || '*' || R1 || '=' || R4 * R1) D,
DECODE(R5, '', '', R5 || '*' || R1 || '=' || R5 * R1) E,
DECODE(R6, '', '', R6 || '*' || R1 || '=' || R6 * R1) F,
DECODE(R7, '', '', R7 || '*' || R1 || '=' || R7 * R1) G,
DECODE(R8, '', '', R8 || '*' || R1 || '=' || R8 * R1) H,
DECODE(R9, '', '', R9 || '*' || R1 || '=' || R9 * R1) I
FROM (SELECT LEVEL R1,
LAG(LEVEL, 1) OVER(ORDER BY LEVEL) R2,
LAG(LEVEL, 2) OVER(ORDER BY LEVEL) R3,
LAG(LEVEL, 3) OVER(ORDER BY LEVEL) R4,
LAG(LEVEL, 4) OVER(ORDER BY LEVEL) R5,
LAG(LEVEL, 5) OVER(ORDER BY LEVEL) R6,
LAG(LEVEL, 6) OVER(ORDER BY LEVEL) R7,
LAG(LEVEL, 7) OVER(ORDER BY LEVEL) R8,
LAG(LEVEL, 8) OVER(ORDER BY LEVEL) R9
FROM DUAL
CONNECT BY LEVEL < 10);

SELECT RN, LTRIM(MAX(SYS_CONNECT_BY_PATH(PRODUCT, ',')), ',') PRODUCT
FROM (SELECT RN,
PRODUCT,
MIN(PRODUCT) OVER(PARTITION BY RN) PRODUCT_MIN,
(ROW_NUMBER() OVER(ORDER BY RN, PRODUCT)) +
(DENSE_RANK() OVER(ORDER BY RN)) NUMID
FROM (SELECT B.RN,
A.RN || '*' || B.RN || '=' || A.RN * B.RN PRODUCT
FROM (SELECT ROWNUM RN FROM ALL_OBJECTS WHERE ROWNUM <= 9) A,
(SELECT ROWNUM RN FROM ALL_OBJECTS WHERE ROWNUM <= 9) B
WHERE A.RN <= B.RN
ORDER BY B.RN, PRODUCT))
START WITH PRODUCT = PRODUCT_MIN
CONNECT BY NUMID - 1 = PRIOR NUMID
GROUP BY RN
ORDER BY RN;

SELECT LTRIM(SYS_CONNECT_BY_PATH(ROWNUM || '*' || LV || '=' ||
RPAD(ROWNUM * LV, 2),
' '))
FROM (SELECT LEVEL LV FROM DUAL CONNECT BY LEVEL < 10)
WHERE LV = 1
CONNECT BY LV + 1 = PRIOR LV;

如何查看正在运行的过程?(转)

通过很多字典可以查看那些过程是否在正在运行中,比如v$access,dba_ddl_locks,v$db_object_cache等,当然通过v$session+v$sql/sqlarea等也是可以做到的,下面给大家介绍一下如何通过v$db_object_cache查看正在运行的过程?


col name format a56
select name
from v$db_object_cache
where locks > 0 and pins > 0 and type='PROCEDURE';

来源:http://xzh2000.itpub.net/post/96/214721

开发库与测试库schema同步的思路及相关过程(转)(可参考)

如果要维护多套开发与测试的数据库环境,如果schema变动很频繁,那dba的工作量也就非常可观,稍一不慎,就会给开发以及测试有不好的影响,所以同步开发与测试环境的是必不可少的,d.c.b.a曾经开发过一个比较并同步schema的工具,但需要手工执行去同步,偶这次介绍的是通过job+procedure来完成的。




1 在源库上创建捕获DDL的触发器与表
a 创建表
create table manager.ddl$trace
(
login_user varchar2(30),
ddl_time date,
program varchar2(64),
sid number,
schema_user varchar2(30),
schema_object varchar2(30),
ddl_sql varchar2(4000),
id number not null,
status number,
errm varchar2(4000)
)
b 创建触发器
create or replace trigger ddl_trigger
before ddl on database
/*
--last modify date:2006-10-18
--last modifier:yekai
--desc:replication ddl to test database
*/
declare
n number;
str_stmt varchar2(4000);
sql_text ora_name_list_t;
l_trace number;
l_sid number;
str_session v$session%rowtype;
begin
--get ddl script
n := ora_sql_txt(sql_text);
for i in 1..n loop
str_stmt := substr(str_stmt||sql_text(i), 1, 3000);
end loop;

--get modify status and permission
select count(*) into l_trace
from dual
where sys_context('userenv','ip_address') is not null
and lower(str_stmt) not like 'truncate% purge snapshot log%'
and lower(str_stmt) not like 'alter% compile%'
and lower(str_stmt) not like 'alter% session%'
and lower(str_stmt) not like '%create%'
and lower(str_stmt) not like '%alter%'
and lower(str_stmt) not like '%drop%'
and lower(str_stmt) not like '%grant%';

--get session information
select * into str_session
from v$session
where sid = (select sid from v$mystat where rownum = 1);

--if not permit then alert
if l_trace > 0 then
--write alert file
sys.dbms_system.ksdwrt(2,'ora-20001:user:'||ora_login_user||',time:'||to_char(sysdate,'yyyymmdd hh24:mi:ss')||',program:'||str_session.program||',ip:'||sys_context('userenv','ip_address')||',object:'||ora_dict_obj_name||',ddl: '||str_stmt);
--raise exception to user
raise_application_error(-20001,'you can not execute ddl on this object except on the local machine');
else
--write information to table
insert into manager.ddl$trace(login_user,ddl_time,program,sid,schema_user,schema_object,ddl_sql,id)
values(ora_login_user,sysdate,str_session.program,l_sid,ora_dict_obj_owner,ora_dict_obj_name,str_stmt,seq_test.nextval);
end if;
exception
when others then
--raise exception to user
raise;
end;
2 在目标库上创建执行动态SQL的过程
create or replace procedure sp_executeddl(v_sql in varchar2)
authid current_user as
begin
execute immediate v_sql;
end;
3 在源库上创建database link
create database link lnk_testdbc connect to test identified by test using 'testdbc';
3 在源库上创建执行同步的过程
create or replace procedure sp_syncddl
as
v_errm varchar2(256);
begin
for i in (select id, ddl_sql from manager.ddl$trace where status is null)
loop
begin
sp_executeddl@lnk_testdbc(i.ddl_sql);
exception
when others then
v_errm := substr(sqlerrm, 1,256);
update manager.ddl$trace
set errm = v_errm,
status = -1
where id = i.id;
end;

update manager.ddl$trace
set status = 1
where id = i.id and status is null;
end loop;

commit;
end sp_syncddl;
4 在源库上创建同步schema的job
var jobid number;
exec dbms_job.submit(:jobid, 'sp_syncddl;', sysdate, 'sysdate+5/1440');

转载: http://xzh2000.itpub.net/post/96/222277

存储过程的四种写法(转)

一个存储过程的四种写法
create table test(
id number(8),
name varchar2(32),
constraint pk_test_id primary key (id)
);

begin
for i in 1..20000 loop
insert into test values(i,'abc');
end loop;
commit;
end;
/




create or replace procedure up_test1
as
cursor cur_tests is select id from test;
begin
for cur_test in cur_tests loop
update test t set name=name||'a' where t.id=cur_test.id;
end loop;
commit;
end;
/
create or replace procedure up_test2
as
cursor cur_tests is select rowid from test;
begin
for cur_test in cur_tests loop
update test t set name=name||'a' where rowid=cur_test.rowid;
end loop;
commit;
end;
/
create or replace procedure up_test3
as
type tv_rowid is table of varchar2(32);
v_rowid tv_rowid;
cursor cur_tests is select rowid from test;
begin
open cur_tests;
fetch cur_tests bulk collect into v_rowid;
for i in 1..v_rowid.count loop
update test t set name=name||'a' where rowid=chartorowid(v_rowid(i));
end loop;
commit;
close cur_tests;
end;
/
create or replace procedure up_test4
as
type tv_rowid is table of varchar2(32);
v_rowid tv_rowid;
cursor cur_tests is select rowid from test;
begin
open cur_tests;
fetch cur_tests bulk collect into v_rowid;
forall i in 1..v_rowid.count
update test t set name=name||'a' where rowid=chartorowid(v_rowid(i));
commit;
close cur_tests;
end;
/

alter session set events '10046 trace name context forever,level 12';
exec up_test1;
exec up_test2;
exec up_test3;
exec up_test4;
alter session set events '10046 trace name context off';

Elapsed: 00:00:06.43
Elapsed: 00:00:06.96
Elapsed: 00:00:05.84
Elapsed: 00:00:04.22

http://xzh2000.itpub.net/post/96/42227

oracle 如何批处理清空多个表,保留表结构(转)

现在测试库有400多个表需要反复清空,用于测试。我在PL/SQL中只能单条用
truncate table1;
truncate table2;
truncate table3;
truncate table4;
......
一次只能选定一条执行,选定多条执行报错,能否写个存储过程,或者批处理,清空时执行下就可以了。



begin
for c in(select t.constraint_name, t.table_name
from USER_CONSTRAINTS t
where t.constraint_type = 'R') loop
EXECUTE IMMEDIATE 'alter table ' ||c.table_name|| ' DISABLE CONSTRAINT '||c.constraint_name;
end loop;
for c1 in(select table_name from user_tables) loop
EXECUTE IMMEDIATE 'truncate table '||c1.table_name;
end loop;
for c2 in(select t.constraint_name, t.table_name
from USER_CONSTRAINTS t
where t.constraint_type = 'R') loop
EXECUTE IMMEDIATE 'alter table ' ||c2.table_name|| ' ENABLE CONSTRAINT '||c2.constraint_name;
end loop;

end;

对大表求min/max注意事项

有一个近亿条记录的表,当需要对主键字段求min/max时,如果在同一条sql中使用min/max时,将会特别的慢,如果分成两条sql执行时,则速度很快,测试如下:




18:22:33 SQL> select min(id),max(id) from bmw_user_trace;
^Cselect min(id),max(id) from bmw_user_trace
*
ERROR at line 1:
ORA-01013: user requested cancel of current operation


Elapsed: 00:00:13.92

18:22:57 SQL> select min(id) from bmw_user_trace;

MIN(ID)
----------
14927731

1 row selected.

Elapsed: 00:00:00.01
18:23:04 SQL> c/min/max
1* select max(id) from bmw_user_trace
18:23:12 SQL> /

MAX(ID)
----------
176547013

1 row selected.

Elapsed: 00:00:00.02

oracle就是按照执行计划里面的RANGE SCAN (MIN/MAX)算法来做的,如果是max,首先沿着最右边的root-branch node-leaf node,发现最右边的leaf block是空的,于是沿着逆向指针往左走,一直走到最左边发现都是空的,于是扫描了所有的leaf blocks如果是min,首先沿着最左边的root-branch node-leaf node,发现最左边的leaf block是空的,于是沿着顺向指针往右走,走到最右边发现都是空的,扫描了所有的leaf blocks。

原文引自http://www.itpub.net/405653.html

COMPILE all PROCEDURE

SELECT DISTINCT 'ALTER PROCEDURE '||NAME||' COMPILE ;'
FROM USER_SOURCE
WHERE TYPE='PROCEDURE'


ALTER PROCEDURE ARTICODRACHV COMPILE ;

SET PAGESIZE 100

DESC USER_SOURCE;

Oracle Sql

监控USER
select distinct
p.spid unix_process,
s.terminal,
to_char(s.logon_time,'YYYY/MON/DD HH24:MI') Logon_Time,
s.username
from v$process p, v$session s
where p.addr=s.paddr order by 2

1. 监控事例的等待:
select event,sum(decode(wait_time,0,0,1)) prev, sum(decode(wait_time,0,1,0)) curr,count(*)
from v$session_wait
group by event order by 4;
2.回滚段的争用情况:
select name,waits,gets,waits/gets ratio from v$rollstat a,v$rollname b where a.usn=b.usn;
3.监控表空间的I/O比例:
select df.tablespace_name name,df.file_name "file",f.phyrds pyr,f.phyblkrd pbr,f.phywrts pyw,
f.phyblkwrt pbw
from v$filestat f,dba_data_files df
where f.file#=df.file_id
4.监空文件系统的I/O比例:
select substr(a.file#,1,2) "#",substr(a.name,1,30) "name",a.status,a.bytes,
b.phyrds,b.phywrts
from v$datafile a,v$filestat b
where a.file#=b.file#
5.在某个用户下找所有的索引:
select user_indexes.table_name, user_indexes.index_name,uniqueness, column_name
from user_ind_columns, user_indexes
where user_ind_columns.index_name = user_indexes.index_name
and user_ind_columns.table_name = user_indexes.table_name
order by user_indexes.table_type, user_indexes.table_name,
user_indexes.index_name, column_position;
6. 监控 SGA 的命中率

select a.value + b.value "logical_reads", c.value "phys_reads",
round(100 * ((a.value+b.value)-c.value) / (a.value+b.value)) "BUFFER HIT RATIO"
from v$sysstat a, v$sysstat b, v$sysstat c
where a.statistic# = 38 and b.statistic# = 39
and c.statistic# = 40;

7. 监控 SGA 中字典缓冲区的命中率

select parameter, gets,Getmisses , getmisses/(gets+getmisses)*100 "miss ratio",
(1-(sum(getmisses)/ (sum(gets)+sum(getmisses))))*100 "Hit ratio"
from v$rowcache
where gets+getmisses <>0
group by parameter, gets, getmisses;

8. 监控 SGA 中共享缓存区的命中率,应该小于1%

select sum(pins) "Total Pins", sum(reloads) "Total Reloads",
sum(reloads)/sum(pins) *100 libcache
from v$librarycache;

select sum(pinhits-reloads)/sum(pins) "hit radio",sum(reloads)/sum(pins) "reload percent"
from v$librarycache;

9. 显示所有数据库对象的类别和大小

select count(name) num_instances ,type ,sum(source_size) source_size ,
sum(parsed_size) parsed_size ,sum(code_size) code_size ,sum(error_size) error_size,
sum(source_size) +sum(parsed_size) +sum(code_size) +sum(error_size) size_required
from dba_object_size
group by type order by 2;

10. 监控 SGA 中重做日志缓存区的命中率,应该小于1%

SELECT name, gets, misses, immediate_gets, immediate_misses,
Decode(gets,0,0,misses/gets*100) ratio1,
Decode(immediate_gets+immediate_misses,0,0,
immediate_misses/(immediate_gets+immediate_misses)*100) ratio2
FROM v$latch WHERE name IN ('redo allocation', 'redo copy');

11. 监控内存和硬盘的排序比率,最好使它小于 .10,增加 sort_area_size

SELECT name, value FROM v$sysstat WHERE name IN ('sorts (memory)', 'sorts (disk)');


12. 监控当前数据库谁在运行什么SQL语句

SELECT osuser, username, sql_text from v$session a, v$sqltext b
where a.sql_address =b.address order by address, piece;

13. 监控字典缓冲区

SELECT (SUM(PINS - RELOADS)) / SUM(PINS) "LIB CACHE" FROM V$LIBRARYCACHE;
SELECT (SUM(GETS - GETMISSES - USAGE - FIXED)) / SUM(GETS) "ROW CACHE" FROM V$ROWCACHE;
SELECT SUM(PINS) "EXECUTIONS", SUM(RELOADS) "CACHE MISSES WHILE EXECUTING" FROM V$LIBRARYCACHE;

后者除以前者,此比率小于1%,接近0%为好。

SELECT SUM(GETS) "DICTIONARY GETS",SUM(GETMISSES) "DICTIONARY CACHE GET MISSES"
FROM V$ROWCACHE

14. 找ORACLE字符集

select * from sys.props$ where name='NLS_CHARACTERSET';

15. 监控 MTS

select busy/(busy+idle) "shared servers busy" from v$dispatcher;

此值大于0.5时,参数需加大

select sum(wait)/sum(totalq) "dispatcher waits" from v$queue where type='dispatcher';
select count(*) from v$dispatcher;
select servers_highwater from v$mts;

servers_highwater接近mts_max_servers时,参数需加大

16. 碎片程度

select tablespace_name,count(tablespace_name) from dba_free_space group by tablespace_name
having count(tablespace_name)>10;

alter tablespace name coalesce;
alter table name deallocate unused;

create or replace view ts_blocks_v as
select tablespace_name,block_id,bytes,blocks,'free space' segment_name from dba_free_space
union all
select tablespace_name,block_id,bytes,blocks,segment_name from dba_extents;

select * from ts_blocks_v;

select tablespace_name,sum(bytes),max(bytes),count(block_id) from dba_free_space
group by tablespace_name;

查看碎片程度高的表

SELECT segment_name table_name , COUNT(*) extents
FROM dba_segments WHERE owner NOT IN ('SYS', 'SYSTEM') GROUP BY segment_name
HAVING COUNT(*) = (SELECT MAX( COUNT(*) ) FROM dba_segments GROUP BY segment_name);

17. 表、索引的存储情况检查

select segment_name,sum(bytes),count(*) ext_quan from dba_extents where
tablespace_name='&tablespace_name' and segment_type='TABLE' group by tablespace_name,segment_name;

select segment_name,count(*) from dba_extents where segment_type='INDEX' and owner='&owner'
group by segment_name;

18、找使用CPU多的用户session

12是cpu used by this session

select a.sid,spid,status,substr(a.program,1,40) prog,a.terminal,osuser,value/60/100 value
from v$session a,v$process b,v$sesstat c
where c.statistic#=12 and c.sid=a.sid and a.paddr=b.addr order by value desc;

20.监控log_buffer的使用情况:(值最好小于1%,否则增加log_buffer 的大小)
select rbar.name,rbar.value,re.name,re.value,(rbar.value*100)/re.value||'%' "radio"
from v$sysstat rbar,v$sysstat re
where rbar.name='redo buffer allocation retries'
and re.name='redo entries';


19、查看运行过的SQL语句:

SELECT SQL_TEXT
FROM V$SQL

常用用户SQL

SQL语句:
表:
  select * from cat;
  select * from tab;
  select table_name from user_tables;
视图:
  select text from user_views where view_name=upper('&view_name');
索引:
  select index_name,table_owner,table_name,tablespace_name,status from user_indexes order by table_name;
触发器:
  select trigger_name,trigger_type,table_owner,table_name,status from user_triggers;
快照:
  select owner,name,master,table_name,last_refresh,next from user_snapshots order by owner,next;
同义词:
  select * from syn;
序列:
  select * from seq;
数据库链路:
  select * from user_db_links;
约束限制:
  select TABLE_NAME,CONSTRAINT_NAME,SEARCH_CONDITION,STATUS
from user_constraints WHERE TABLE_name=upper('&TABLE_Name');
本用户读取其它用户对象的权限:
  select * from user_tab_privs;
本用户所拥有的系统权限:
  select * from user_sys_privs;
用户:
  select * from all_users order by user_id;
表空间剩余自由空间情况:
  select tablespace_name,sum(bytes) 总字节数,max(bytes),count(*) from dba_free_space group by tablespace_name;
数据字典:
  select table_name from dict order by table_name;
锁及资源信息:
  select * from v$lock;不包括DDL锁
数据库字符集:
  select name,value$ from props$ where name='NLS_CHARACTERSET';
inin.ora参数:
  select name,value from v$parameter order by name;
SQL共享池:
  select sql_text from v$sqlarea;
数据库:
  select * from v$database
控制文件:
  select * from V$controlfile;
重做日志文件信息:
  select * from V$logfile;
来自控制文件中的日志文件信息:
  select * from V$log;
来自控制文件中的数据文件信息:
  select * from V$datafile;
NLS参数当前值:
  select * from V$nls_parameters;
ORACLE版本信息:
  select * from v$version;
描述后台进程:
  select * from v$bgprocess;
查看版本信息:
  select * from product_component_version;

查询表结构

select substr(table_name,1,20) tabname,
substr(column_name,1,20)column_name,
rtrim(data_type)||'('||data_length||')' from system.dba_tab_columns
where owner='username'

表空间使用状态

select a.file_id "FileNo",a.tablespace_name "Tablespace_name",
round(a.bytes/1024/1024,4) "Total MB",
round((a.bytes-sum(nvl(b.bytes,0)))/1024/1024,4) "Used MB",
round(sum(nvl(b.bytes,0))/1024/1024,4) "Free MB",
round(sum(nvl(b.bytes,0))/a.bytes*100,4) "%Free"
from dba_data_files a, dba_free_space b
where a.file_id=b.file_id(+)
group by a.tablespace_name,
a.file_id,a.bytes order by a.tablespace_name


查询某个模式下面数据不为空的表

declare
Cursor c is select TNAME from tab;
vCount Number;
table_nm Varchar2(100);
sq varchar2(300);
begin
for r in c loop
table_nm:=r.TNAME;
sq:='select count(*) from '|| table_nm;
execute immediate sq into vCount;
if vCount>0 then
dbms_output.put_line(r.tname);
end if;
end loop;
end;


客户端主机信息

SELECT
SYS_CONTEXT('USERENV','TERMINAL') TERMINAL,
SYS_CONTEXT('USERENV','HOST') HOST,
SYS_CONTEXT('USERENV','OS_USER') OS_USER,
SYS_CONTEXT('USERENV','IP_ADDRESS') IP_ADDRESS
FROM DUAL

安装Oracle后,经常使用的修改表空间的SQL代码

配置:
Windows NT 4.0 中文版
5块10.2GB SCSI硬盘
分:C:盘、D:盘、E:盘、F:盘、G:盘
Oracle 8.0.4 for Windows NT
NT安装在C:\WINNT,Oracle安装在C:\ORANT

目标:
因系统的回滚段太小,现打算生成新的回滚段,
建立大的、新的表空间(数据表空间、索引表空间、回滚表空间、临时表空间、)
建两个数据表空间、两个索引表空间,这样建的目的是根据实际应用,
如:现有10个应用用户,每个用户是一个独立子系统(如:商业进销存MIS系统中的财务、收款、库存、人事、总经理等)
尤其大型商场中收款机众多,同时访问进程很多,经常达到50-100个进程同时访问,
这样,通过建立多个用户表空间、索引表空间,把各个用户分别建在不同的表空间里(多个用户表空间放在不同的物理磁盘上),
减少了用户之间的I/O竞争、读写数据与写读索引的竞争(用户表空间、索引表空间也分别放在不同的物理磁盘上)

规划:
C:盘、NT系统,Oracle系统
D:盘、数据表空间1(3GB、自动扩展)、回滚表空间1(1GB、自动扩展)
E:盘、数据表空间2(3GB、自动扩展)、回滚表空间2(1GB、自动扩展)
F:盘、索引表空间1(2GB、自动扩展)、临时表空间1(0.5GB、不自动扩展)
G:盘、索引表空间2(2GB、自动扩展)、临时表空间2(0.5GB、不自动扩展)

注:这只是一个简单的规划,实际规划要依系统需求来定,尽量减少I/O竞争

实现:
1、首先查看系统有哪些回滚段及其状态。

SQL> col owner format a20
SQL> col status format a10
SQL> col segment_name format a20
SQL> col tablespace_name format a20

SQL> SELECT OWNER,SEGMENT_NAME,TABLESPACE_NAME,SUM(BYTES)/1024/1024 M
2 FROM DBA_SEGMENTS
3 WHERE SEGMENT_TYPE='ROLLBACK'
4 GROUP BY OWNER,SEGMENT_NAME,TABLESPACE_NAME
5 /

OWNER SEGMENT_NAME TABLESPACE_NAME M
-------------------- -------------------- -------------------- ---------
SYS RB1 ROLLBACK_DATA .09765625
SYS RB10 ROLLBACK_DATA .09765625
SYS RB11 ROLLBACK_DATA .09765625
SYS RB12 ROLLBACK_DATA .09765625
SYS RB13 ROLLBACK_DATA .09765625
SYS RB14 ROLLBACK_DATA .09765625
SYS RB15 ROLLBACK_DATA .09765625
SYS RB16 ROLLBACK_DATA .09765625
SYS RB2 ROLLBACK_DATA .09765625
SYS RB3 ROLLBACK_DATA .09765625
SYS RB4 ROLLBACK_DATA .09765625
SYS RB5 ROLLBACK_DATA .09765625
SYS RB6 ROLLBACK_DATA .09765625
SYS RB7 ROLLBACK_DATA .09765625
SYS RB8 ROLLBACK_DATA .09765625
SYS RB9 ROLLBACK_DATA .09765625
SYS RB_TEMP SYSTEM .24414063
SYS SYSTEM SYSTEM .1953125

查询到18记录.

SQL> SELECT SEGMENT_NAME,OWNER,
2 TABLESPACE_NAME,SEGMENT_ID,FILE_ID,STATUS
3 FROM DBA_ROLLBACK_SEGS
4 /

SEGMENT_NAME OWNER TABLESPACE_NAME SEGMENT_ID FILE_ID STATUS
-------------------- -------------------- -------------------- ---------- --------- ----------
SYSTEM SYS SYSTEM 0 1 ONLINE
RB_TEMP SYS SYSTEM 1 1 OFFLINE
RB1 PUBLIC ROLLBACK_DATA 2 3 ONLINE
RB2 PUBLIC ROLLBACK_DATA 3 3 ONLINE
RB3 PUBLIC ROLLBACK_DATA 4 3 ONLINE
RB4 PUBLIC ROLLBACK_DATA 5 3 ONLINE
RB5 PUBLIC ROLLBACK_DATA 6 3 ONLINE
RB6 PUBLIC ROLLBACK_DATA 7 3 OFFLINE
RB7 PUBLIC ROLLBACK_DATA 8 3 OFFLINE
RB8 PUBLIC ROLLBACK_DATA 9 3 OFFLINE
RB9 PUBLIC ROLLBACK_DATA 10 3 OFFLINE
RB10 PUBLIC ROLLBACK_DATA 11 3 OFFLINE
RB11 PUBLIC ROLLBACK_DATA 12 3 OFFLINE
RB12 PUBLIC ROLLBACK_DATA 13 3 OFFLINE
RB13 PUBLIC ROLLBACK_DATA 14 3 OFFLINE
RB14 PUBLIC ROLLBACK_DATA 15 3 OFFLINE
RB15 PUBLIC ROLLBACK_DATA 16 3 OFFLINE
RB16 PUBLIC ROLLBACK_DATA 17 3 OFFLINE

查询到18记录.

2、修改代码如下,可把以下代码存入一.sql文件,如cg_sys.sql,然后以SQL> @cg_sys.sql调用执行。

--注意:各个硬盘上要事先建好oradata目录

--修改现有回滚段,使之失效,下线
alter rollback segment rb1 offline;
alter rollback segment rb2 offline;
alter rollback segment rb3 offline;
alter rollback segment rb4 offline;
alter rollback segment rb5 offline;
alter rollback segment rb6 offline;
alter rollback segment rb7 offline;
alter rollback segment rb8 offline;
alter rollback segment rb9 offline;
alter rollback segment rb10 offline;
alter rollback segment rb11 offline;
alter rollback segment rb12 offline;
alter rollback segment rb13 offline;
alter rollback segment rb14 offline;
alter rollback segment rb15 offline;
alter rollback segment rb16 offline;

--删除原有回滚段
drop rollback segment rb1;
drop rollback segment rb2;
drop rollback segment rb3;
drop rollback segment rb4;
drop rollback segment rb5;
drop rollback segment rb6;
drop rollback segment rb7;
drop rollback segment rb8;
drop rollback segment rb9;
drop rollback segment rb10;
drop rollback segment rb11;
drop rollback segment rb12;
drop rollback segment rb13;
drop rollback segment rb14;
drop rollback segment rb15;
drop rollback segment rb16;

--建数据表空间1
--收款、库存、订货、远程通信
create tablespace USER_DATA1 datafile
'd:\oradata\user1_1.ora' size 512M,
'd:\oradata\user1_2.ora' size 512M,
'd:\oradata\user1_3.ora' size 512M,
'd:\oradata\user1_4.ora' size 512M,
'd:\oradata\user1_5.ora' size 512M,
'd:\oradata\user1_6.ora' size 512M
AUTOEXTEND ON NEXT 5M MAXSIZE UNLIMITED
default storage (initial 128K next 2M pctincrease 0);
--initial 128K,因为,用户建在表空间上,而表建在用户里,为用户所拥有,
--用户继承数据表空间的存储参数,表继承用户的存储参数
--如果initial设的过大,如:5M,则每建一个空表就要占用5M的空间,即使一条记录也没有
--AUTOEXTEND ON NEXT 5M MAXSIZE UNLIMITED,设置数据文件自动扩展,每一次扩展增加5M,最大空间不受限

--建数据表空间2
--物价、人事、结算、财务、总经理、合同、统计
create tablespace USER_DATA2 datafile
'e:\oradata\user2_1.ora' size 512M,
'e:\oradata\user2_2.ora' size 512M,
'e:\oradata\user2_3.ora' size 512M,
'e:\oradata\user2_4.ora' size 512M,
'e:\oradata\user2_5.ora' size 512M,
'e:\oradata\user2_6.ora' size 512M
AUTOEXTEND ON NEXT 5M MAXSIZE UNLIMITED
default storage (initial 128K next 2M pctincrease 0);

--建索引表空间1
create tablespace INDEX_DATA1 datafile
'f:\oradata\index1_1.ora' size 512M,
'f:\oradata\index1_2.ora' size 512M,
'f:\oradata\index1_3.ora' size 512M,
'f:\oradata\index1_4.ora' size 512M
AUTOEXTEND ON NEXT 5M MAXSIZE UNLIMITED
default storage (initial 128K next 2M pctincrease 0);

--建索引表空间2
create tablespace INDEX_DATA2 datafile
'g:\oradata\index2_1.ora' size 512M,
'g:\oradata\index2_2.ora' size 512M,
'g:\oradata\index2_3.ora' size 512M,
'g:\oradata\index2_4.ora' size 512M
AUTOEXTEND ON NEXT 5M MAXSIZE UNLIMITED
default storage (initial 128K next 2M pctincrease 0);

--建回滚表空间1
--设置初始值40M(initial 40M),则每在这个表空间中建一个回滚段,
--此回滚段自动继承此回滚表空间的存储参数,也即默认文件为40M
create tablespace ROLLBACK_DATA1 datafile
'd:\oradata\roll1_1.ora' size 512M,
'd:\oradata\roll1_2.ora' size 512M
AUTOEXTEND ON NEXT 5M MAXSIZE UNLIMITED
default storage (initial 40M next 5M pctincrease 0);

--建回滚表空间2
create tablespace ROLLBACK_DATA2 datafile
'e:\oradata\roll2_1.ora' size 512M,
'e:\oradata\roll2_2.ora' size 512M
AUTOEXTEND ON NEXT 5M MAXSIZE UNLIMITED
default storage (initial 40M next 5M pctincrease 0);

--建临时表空间1
create tablespace TEMPORARY_DATA1 datafile
'f:\oradata\temp1_1.ora' size 512M
default storage (initial 10M next 3M pctincrease 0);

--建临时表空间2
create tablespace TEMPORARY_DATA2 datafile
'g:\oradata\temp2_1.ora' size 512M
default storage (initial 10M next 3M pctincrease 0);

--使其真正成为临时的
alter tablespace TEMPORARY_DATA1 temporary;
alter tablespace TEMPORARY_DATA2 temporary;

--建立新的回滚段,每个都一样大,不同大小的回滚段没有什么意义,系统是随机选择的。
--建多少个,根据并发访问用户的多少,
--如果你们公司每天有50-100个人员使用Oracle系统开发的管理软件,应该20个以上

create public rollback segment rb01 tablespace rollback_data1;
create public rollback segment rb02 tablespace rollback_data1;
create public rollback segment rb03 tablespace rollback_data1;
create public rollback segment rb04 tablespace rollback_data1;
create public rollback segment rb05 tablespace rollback_data1;
create public rollback segment rb06 tablespace rollback_data1;
create public rollback segment rb07 tablespace rollback_data1;
create public rollback segment rb08 tablespace rollback_data1;
create public rollback segment rb09 tablespace rollback_data2;
create public rollback segment rb10 tablespace rollback_data2;
--前8个建在回滚表空间1中,后8个在回滚表空间2
create public rollback segment rb11 tablespace rollback_data2;
create public rollback segment rb12 tablespace rollback_data2;
create public rollback segment rb13 tablespace rollback_data2;
create public rollback segment rb14 tablespace rollback_data2;
create public rollback segment rb15 tablespace rollback_data2;
create public rollback segment rb16 tablespace rollback_data2;
create public rollback segment rb17 tablespace rollback_data2;
create public rollback segment rb18 tablespace rollback_data2;
create public rollback segment rb19 tablespace rollback_data2;
create public rollback segment rb20 tablespace rollback_data2;

--使回滚段online,即有效
alter rollback segment rb01 online;
alter rollback segment rb02 online;
alter rollback segment rb03 online;
alter rollback segment rb04 online;
alter rollback segment rb05 online;
alter rollback segment rb06 online;
alter rollback segment rb07 online;
alter rollback segment rb08 online;
alter rollback segment rb09 online;
alter rollback segment rb10 online;
alter rollback segment rb11 online;
alter rollback segment rb12 online;
alter rollback segment rb13 online;
alter rollback segment rb14 online;
alter rollback segment rb15 online;
alter rollback segment rb16 online;
alter rollback segment rb17 online;
alter rollback segment rb18 online;
alter rollback segment rb19 online;
alter rollback segment rb20 online;

--查看现有回滚段及其状态
col segment format a30
SELECT SEGMENT_NAME,OWNER,TABLESPACE_NAME,SEGMENT_ID,FILE_ID,STATUS FROM DBA_ROLLBACK_SEGS;

--查看数据文件及其所在表空间、大小、状态
col file_name format a40
col tablespace_name format a20
select file_name,file_id,tablespace_name,bytes,status from dba_data_files;


至此,表空间重新规划完毕,这里讲的比较通俗,还有好多参数值得设置,能够把Oracle设置到最优的境界,
表空间设置完了,下面,就该好好的整理一下Oracle的内存区了,
Oracle很有意思,内存越大,效果越明显,所以有必要好好调整一下SGA区,也就是主要配置ininorcl.ora参数文件。


查看回滚段名称及大小

COLUMN roll_name FORMAT a13 HEADING 'Rollback Name'
COLUMN tablespace FORMAT a11 HEADING 'Tablspace'
COLUMN in_extents FORMAT a20 HEADING 'Init/Next Extents'
COLUMN m_extents FORMAT a10 HEADING 'Min/Max Extents'
COLUMN status FORMAT a8 HEADING 'Status'
COLUMN wraps FORMAT 999 HEADING 'Wraps'
COLUMN shrinks FORMAT 999 HEADING 'Shrinks'
COLUMN opt FORMAT 999,999,999 HEADING 'Opt. Size'
COLUMN bytes FORMAT 999,999,999 HEADING 'Bytes'
COLUMN extents FORMAT 999 HEADING 'Extents'

SELECT
a.owner || '.' || a.segment_name roll_name
, a.tablespace_name tablespace
, TO_CHAR(a.initial_extent) || ' / ' ||
TO_CHAR(a.next_extent) in_extents
, TO_CHAR(a.min_extents) || ' / ' ||
TO_CHAR(a.max_extents) m_extents
, a.status status
, b.bytes bytes
, b.extents extents
, d.shrinks shrinks
, d.wraps wraps
, d.optsize opt
FROM
dba_rollback_segs a
, dba_segments b
, v$rollname c
, v$rollstat d
WHERE
a.segment_name = b.segment_name
AND a.segment_name = c.name (+)
AND c.usn = d.usn (+)
ORDER BY a.segment_name;


PL/SQL入门教程

PL/SQL入门教程


1.1 PL/SQL简介

PL/SQL是ORACLE的过程化语言,包括一整套的数据类型、条件结构、循环结构和异常处理结构,PL/SQL可以执行SQL语句,SQL语句中也可以使用PL/SQL函数。

1.2 创建PL/SQL程序块

DECLARE

BEGIN

EXCEPTION
END;
1.3 PL/SQL数据类型

名称
类型
说明

NUMBER
数字型
能存放整数值和实数值,并且可以定义精度和取值范围

BINARY_INTEGER
数字型
可存储带符号整数,为整数计算优化性能

DEC
数字型
NUMBER的子类型,小数

DOUBLE PRECISION
数字型
NUMBER的子类型,高精度实数

INTEGER
数字型
NUMBER的子类型,整数

INT
数字型
NUMBER的子类型,整数

NUMERIC
数字型
NUMBER的子类型,与NUMBER等价

REAL
数字型
NUMBER的子类型,与NUMBER等价

SMALLINT
数字型
NUMBER的子类型,取值范围比INTEGER小

VARCHAR2
字符型
存放可变长字符串,有最大长度

CHAR
字符型
定长字符串

LONG
字符型
变长字符串,最大长度可达32,767

DATE
日期型
以数据库相同的格式存放日期值

BOOLEAN
布尔型
TRUE OR FALSE

ROWID
ROWID
存放数据库的行号


例子:
DECLARE
ORDER_NO NUMBER(3);
CUST_NAME VARCHAR2(20);
ORDER_DATE DATE;
EMP_NO INTEGER:=25;
PI CONSTANT NUMBER:=3.1416;
BEGIN
NULL;
END;
1.4 处理PL/SQL的异常

1.4.1 PL/SQL的异常

例如:
DECLARE
X NUMBER;
BEGIN
X:= 'yyyy';--Error Here
EXCEPTION WHEN VALUE_ERROR THEN
DBMS_OUTPUT.PUT_LINE('EXCEPTION HANDED');
END;

实现技术:
EXCEPTION WHEN first_exception THEN

WHEN second_exception THEN

WHEN OTHERS THEN
/*THERS异常处理器必须排在最后,它处理所有没有明确列出的异常。*/

END;

1.4.2 预定义异常

异常名称
ORACLE错误
说明

CURSOR_ALREADY_OPEN
ORA-6511
试图打开一个已打开的光标

DUP_VAL_ON_INDEX
ORA-0001
试图破坏一个唯一性限制

INVALID_CURSOR
ORA-1001
试图使用一个无效的光标

INVALID_NUMBER
ORA-1722
试图对非数字值进行数字操作

LOGIN_DENIED
ORA-1017
无效的用户名或者口令

NO_DATA_FOUND
ORA-1403
查询未找到数据

NOT_LOGGED_ON
ORA-1012
还未连接就试图数据库操作

PROGRAM_ERROR
ORA-6501
内部错误

ROWTYPE_MISMATCH
ORA-6504
主变量和光标的类型不兼容

STORAGE_ERROR
ORA-6500
内部错误

TIMEOUT_ON_RESOURCE
ORA-0051
发生超时

TOO_MANY_ROWS
ORA-1422
SELECT INTD命令返回的多行

TRANSACTION_BACKED_OUT
ORA-006
由于死锁提交被退回

VALUE_ERROR
ORA-6502
转换或者裁剪错误

ZERO_DIVIDE
ORA-1476
试图被零除


 

1.4.3 自定义异常处理

DECLARE
BAD_ROWID EXCEPTION;
X ROWID;
PRAGMA EXCEPTION_INIT(BAD_ROWID,-01445);
BEGIN
SELECT ROWID INTO X FROM TAB
WHERE ROWNUM=1;
EXCEPTION WHEN BAD_ROWID THEN
DBMS_OUTPUT.PUT_LINE('CANNOT QUERY ROWID FROM THIS VIEW');
END;

注意:-01445 因为PRAGMA EXCEPTION_INIT命令把这个变量(-01455)连接到
这个ORACLE错误,该语句的语法如下:
PRAGMA EXCEPTION_INIT(exception_name, error_number);
其中error_number是负数,因为错误号被认为负数,当定义错误时记住使用负号

1.4.4 自定义异常

异常不一定必须是oracle返回的系统错误,用户可以在自己的应用程序中创
建可触发及可处理的自定义异常
DECLARE
SALARY_CODE VARCHAR2(1);
INVALID_SALARY_CODE EXCEPTION;
BEGIN
SALARY_CODE:='X';
IF SALARY_CODE NOT IN('A', 'B', 'C') THEN
RAISE INVALID_SALARY_CODE;
END IF;
EXCEPTION WHEN INVALID_SALARY_CODE THEN
DBMS_OUTPUT.PUT_LINE('INVALID SALARY CODE');
END;

1.5 在PL/SQL中单条记录的查询

在PL/SQL内,有时在没有定义显式光标的情况下需要查询单条记录,并把记录的数据赋给变量。
DECLARE
ln_dno NUMBER;
lvs_dname VARCHAR2(40);
BEGIN
SELECT DEPT_NO,DEPT_NAME
INTO ln_dno,lvs_dname
FROM dept
WHERE DEPT_NO=1;
DBMS_OUTPUT.PUT_LINE(TO_CHAR(ln_dno)||'.'||lvs_dname);
EXCEPTION WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE('NO DATA_FOUND');
WHEN TOO_MANY_ROWS THEN
DBMS_OUTPUT.PUT_LINE('TOO_MANY_ROWS');
END;

1.6 用光标查询多条记录

光标(CURSOR)是指向一个称为上下文相关区的区域的指针,这个区域在服务器的处理过程全局区(PGA)内,当服务器上执行了一个查询后,查询返回的记录集存放在上下文相关区,通过光标上的操作可以把这些记录检索到客户端的应用程序。

1.6.1 使用光标的基本方法

DECLARE
CURSOR C1 IS SELECT VIEW_NAME FROM ALL_VIEWS
WHERE ROWNUM<=10
ORDER BY VIEW_NAME;
VNAME VARCHAR2(40);
BEGIN
OPEN C1;
FETCH C1 INTO VNAME;
WHILE C1%FOUND LOOP
DBMS_OUTPUT.PUT_LINE(TO_CHAR(C1%ROWCOUNT)||' '||VNAME);
FETCH C1 INTO VNAME;
END LOOP;
END;

属性
含量

%FOUND
布尔型属性,当最近一次该记录时成功返回,则值为TRUE

%NOTFOUND
布尔型属性,它的值总与%FOUND属性的值相反

%ISOPEN
布尔型属性,当光标是打开时返回TRUE

%ROWCOUNT
数字型属性,返回已从光标中读取的记录数


 

1.6.2 使用光标FOR循环

DECLARE
CURSOR C1 IS
SELECT VIEW_NAME
FROM ALL_VIEWS
WHERE ROWNUM<=10
ORDER BY VIEW_NAME;
BEGIN
FOR I IN C1 LOOP
DBMS_OUTPUT.PUT_LINE(I.VIEW_NAME);
END LOOP;
END LOOP;
EXCEPTION WHEN OTHERS THEN
NULL;
END;

1.6.3 带参数的光标

DECLARE
CURSOR C1(VIEW_PATTERN VARCHAR2) IS
SELECT VIEW_NAME
FROM ALL_VIEWS
WHERE VIEW_NAME LIKE VIEW_PATTERN||'%' AND
ROWNUM<=10
ORDER BY VIEW_NAME;
VNAME VARCHAR2(40);
BEGIN
FOR I IN C1('USER_AR') LOOP
DBMS_OUTPUT.PUT_LINE(I.VIEW_NAME);
END LOOP;
DBMS_OUTPUT.PUT_LINE();
FOR I IN C1('USER') LOOP
DBMS_OUTPUT.PUT_LINE(I.VIEW_NAME);
END LOOP;
EXCEPTION WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('AAA');
END;

1.7 创建代表数据库记录和列的变量

变量名 基表名.列名%TYPE
DECLARE
D_NO DEPT.DEPT_NO%TYPE;
D_NAME DEPT.DEPT_NAME%TYPE;
BEGIN
SELECT DEPT_NO,DEPT_NAME INTO D_NO,D_NAME
FROM DEPT;
DBMS_OUTPUT.PUT_LINE(TO_CHAR(D_NO));
EXCEPTION WHEN NO_DATA_FOUND THEN
NULL;
END;

变量名 基表名%ROWTYPE
DECLARE
D VEQU12%ROWTYPE;
BEGIN
SELECT ASSET12ID,ASSET12NAME
INTO D.ASSET12ID, D.ASSET12NAME
FROM VEQU12;
DBMS_OUTPUT.PUT_LINE(D.ASSET12ID);
EXCEPTION
WHEN NO_DATA_FOUND THEN
NULL;
WHEN TOO_MANY_ROWS THEN
DBMS_OUTPUT.PUT_LINE('TOO_MANY_ROWS');
END;
说明:
当用户要创建一个变量来表示一个基表列或者要创建多个变量来代表一整条记录时,可以实际使用%TYPE属性和%ROWTYPE属性,使用%TYPE属性和%ROWTYPE属性可以保证当基表的结构或者其中某列的数据类型改变了时,用户的PL/SQL代码仍可正常工作。

1.9 怎样用PL/SQL表实现数组功能

PL/SQL表与其它过程化语言(如C语言)的一维数组类似。实现PL/SQL表需要创建一个数据类型并另外进行变量说明。
Type <类型名> Is
Table Of <数据类型>
Index by Binary_Integer;
以下为一个例子:
Declare
Type Array_type is
Table Of Number
Index by Binary_Integer;
My_Array Array_type;
Begin
For I In 1..10 Loop
My_Array(I) := I*2;
End Loop;
For I In 1..10 Loop
Dbms_Output.Put_line(To_char(My_Array(I)));
End Loop;
End;

在from后面使用变量

CREATE OR REPLACE FUNCTION GET_TABLE_COUNT(
I_TabNa IN VARCHAR2 ,
I_Owner IN VARCHAR2 DEFAULT NULL
)
RETURN NUMBER
IS
V_RtnVal NUMBER ;
V_CursorId INTEGER ;
V_SqlStr VARCHAR2(300) ;
BEGIN
V_CursorId := DBMS_SQL.OPEN_CURSOR ;

IF LENGTHB( RTRIM( LTRIM( NVL( I_Owner , '' ) ) ) ) = 0 THEN
V_SqlStr := 'SELECT COUNT(*) FROM ' || I_TabNa ;
ELSE
V_SqlStr := 'SELECT COUNT(*) FROM ' || I_Owner|| '.' || I_TabNa ;
END IF ;

DBMS_SQL.PARSE( V_CursorId , V_SqlStr , DBMS_SQL.V7 ) ;

DBMS_SQL.DEFINE_COLUMN( V_CursorId , 1 , 0 ) ;

IF DBMS_SQL.EXECUTE( V_CursorId ) = 0 THEN
NULL ;
END IF ;

IF DBMS_SQL.FETCH_ROWS( V_CursorId ) = 0 THEN
RETURN 0 ;
END IF ;

DBMS_SQL.COLUMN_VALUE( V_CursorId , 1 , V_RtnVal ) ;

DBMS_SQL.CLOSE_CURSOR( V_CursorId ) ;

RETURN V_RtnVal ;
EXCEPTION
WHEN OTHERS THEN
DBMS_SQL.CLOSE_CURSOR( V_CursorId ) ;
-- DBMS_OUTPUT.PUT_LINE( V_SqlStr || SQLERRM ) ;
RETURN 0 ;
END GET_TABLE_COUNT;


试验结果:
SQL> select GET_TABLE_COUNT( 'tab' ) from dual ;

GET_TABLE_COUNT('TAB')
----------------------
22

SQL> select GET_TABLE_COUNT( 'spr' , 'testman') from dual ;

GET_TABLE_COUNT('SPR','TESTMAN
------------------------------
15

SQL> select GET_TABLE_COUNT( 'U_Oausr' , 'tm') from dual ;

GET_TABLE_COUNT('U_OAUSR','TM'
------------------------------
10

SQL>

说明:
-- DBMS_SQL.DEFINE_COLUMN( V_CursorId , 1 , 0 ) ; 里的“0”是什么意思?
DEFINE_COLUMN是用作定义数据类型的,不同的数据类型有不太的定义方式,这里面的“0”通俗点说就是“与‘0’一样的数据类型的意思”,比如定义长度为200的varchar2型的列的时候,可以简化为这样定义:DBMS_SQL.DEFINE_COLUMN( V_CursorId , 1 , 'tmpStr' , 200 ),更多的数据类型列的定义请查看oracle的pl/sql文档,里面很全。
-- 另外,怎么用联编变量?
联编变量是一种非常好的传递参数的方式,而且不容易出错。但是既然称之为“联编变量”那就是它只能对Oracle中认为的变量进行联编,而刚才上面的例子中,表面是不能够作为变量的,因此不可以联编,Oracle中认为出现在逻辑表达式右边的才是变量,例如可以这样进行联编变量:
......
V_SqlStr := 'SELECT COUNT(*) FROM TAB WHERE TName LIKE :I_Arg0 ' ;

DBMS_SQL.PARSE( V_CursorId , V_SqlStr , DBMS_SQL.V7 ) ;
V_TabName := 'MYTAB' ;
DBMS_SQL.BIND_VARIABLE( V_CursorId , ':I_Arg0' , V_TabName || '%' ) ;
......


8i以后的版本这样写也行
CREATE OR REPLACE FUNCTION GET_TABLE_COUNT(
I_TabNa IN VARCHAR2 ,
I_Owner IN VARCHAR2 DEFAULT NULL
)
RETURN NUMBER
IS
V_RtnVal NUMBER ;
V_TabName VARCHAR2(300) ;
BEGIN
IF LENGTHB( RTRIM( LTRIM( NVL( I_Owner , '' ) ) ) ) = 0 THEN
V_TabName := I_TabNa ;
ELSE
V_TabName := I_Owner|| '.' || I_TabNa ;
END IF ;

EXECUTE IMMEDIATE 'SELECT COUNT(*) FROM ' || V_TabName INTO V_RtnVal ;
RETURN V_RtnVal ;

EXCEPTION
WHEN OTHERS THEN
RETURN 0 ;
END GET_TABLE_COUNT ;


Oracle常用数据字典

视图名 描述
ALL_CATALOG All tables, views, synonyms, sequences accessible to the user
ALL_COL_COMMENTS Comments on columns of accessible tables and views
ALL_COL_GRANTS_MADE Grants on columns for which the user is owner or grantor
ALL_COL_GRANTS_RECD Grants on columns for which the user or PUBLIC is the grantee
ALL_COL_PRIVS Grants on columns for which the user is the grantor, grantee, owner, or an enabled role or PUBLIC is the grantee
ALL_COL_PRIVS_MADE Grants on columns for which the user is owner or grantor
ALL_COL_PRIVS_RECD Grants on columns for which the user, PUBLIC or enabled role is the grantee
ALL_CONSTRAINTS Constraint definitions on accessible tables
ALL_CONS_COLUMNS Information about accessible columns in constraint definitions
ALL_DB_LINKS Database links accessible to the user
ALL_DEF_AUDIT_OPTS Auditing options for newly created objects
ALL_DEPENDENCIES Dependencies to and from objects accessible to the user
ALL_ERRORS Current errors on stored objects that user is allowed to create
ALL_INDEXES Descriptions of indexes on tables accessible to the user
ALL_IND_COLUMNS COLUMNs comprising INDEXes on accessible TABLES
ALL_OBJECTS Objects accessible to the user
ALL_REFRESH All the refresh groups that the user can touch
ALL_REFRESH_CHILDREN All the objects in refresh groups, where the user can touch the group
ALL_SEQUENCES Description of SEQUENCEs accessible to the user
ALL_SNAPSHOTS Snapshots the user can look at
ALL_SOURCE Current source on stored objects that user is allowed to create
ALL_SYNONYMS All synonyms accessible to the user
ALL_TABLES Description of tables accessible to the user
ALL_TAB_COLUMNS Columns of all tables, views and clusters
ALL_TAB_COMMENTS Comments on tables and views accessible to the user
ALL_TAB_GRANTS_MADE User's grants and grants on user's objects
ALL_TAB_GRANTS_RECD Grants on objects for which the user or PUBLIC is the grantee
ALL_TAB_PRIVS Grants on objects for which the user is the grantor, grantee, owner, or an enabled role or PUBLIC is the grantee
ALL_TAB_PRIVS_MADE User's grants and grants on user's objects
ALL_TAB_PRIVS_RECD Grants on objects for which the user, PUBLIC or enabled role is the grantee
ALL_TRIGGERS Triggers accessible to the current user
ALL_TRIGGER_COLS Column usage in user's triggers or in triggers on user's tables
ALL_USERS Information about all users of the database
ALL_VIEWS Text of views accessible to the user
USER_AUDIT_CONNECT Audit trail entries for user logons/logoffs
USER_AUDIT_OBJECT Audit trail records for statements concerning objects, specifically: table, cluster, view, index, sequence, [public] database link, [public] synonym, procedure, trigger, rollback segment, tablespace, role, user
USER_AUDIT_SESSION  
USER_AUDIT_STATEMENT Audit trail records concerning grant, revoke, audit, noaudit and alter system
USER_AUDIT_TRAIL Audit trail entries relevant to the user
USER_CATALOG Tables, Views, Synonyms and Sequences owned by the user
USER_CLUSTERS Descriptions of user's own clusters
USER_CLU_COLUMNS Mapping of table columns to cluster columns
USER_COL_COMMENTS Comments on columns of user's tables and views
USER_COL_GRANTS Grants on columns for which the user is the owner, grantor or grantee
USER_COL_GRANTS_MADE All grants on columns of objects owned by the user
USER_COL_GRANTS_RECD Grants on columns for which the user is the grantee
USER_COL_PRIVS Grants on columns for which the user is the owner, grantor or grantee
USER_COL_PRIVS_MADE All grants on columns of objects owned by the user
USER_COL_PRIVS_RECD Grants on columns for which the user is the grantee
USER_CONSTRAINTS Constraint definitions on user's own tables
USER_CONS_COLUMNS Information about accessible columns in constraint definitions
USER_CROSS_REFS Cross references for user's views and synonyms
USER_DB_LINKS Database links owned by the user
USER_DEPENDENCIES Dependencies to and from a users objects
USER_ERRORS Current errors on stored objects owned by the user
USER_EXTENTS Extents comprising segments owned by the user
USER_FREE_SPACE Free extents in tablespaces accessible to the user
USER_INDEXES Description of the user's own indexes
USER_IND_COLUMNS COLUMNs comprising user's INDEXes or on user's TABLES
USER_JOBS All jobs owned by this user
USER_OBJECTS Objects owned by the user
USER_OBJECT_SIZE Sizes, in bytes, of various pl/sql objects
USER_OBJ_AUDIT_OPTS Auditing options for user's own tables and views
USER_REFRESH All the refresh groups
USER_REFRESH_CHILDREN All the objects in refresh groups, where the user owns the refresh group
USER_RESOURCE_LIMITS Display resource limit of the user
USER_ROLE_PRIVS Roles granted to current user
USER_SEGMENTS Storage allocated for all database segments
USER_SEQUENCES Description of the user's own SEQUENCEs
USER_SNAPSHOTS Snapshots the user can look at
USER_SNAPSHOT_LOGS All snapshot logs owned by the user
USER_SOURCE Source of stored objects accessible to the user
USER_SYNONYMS The user's private synonyms
USER_SYS_PRIVS System privileges granted to current user
USER_TABLES Description of the user's own tables
USER_TABLESPACES Description of accessible tablespaces
USER_TAB_AUDIT_OPTS Auditing options for user's own tables and views
USER_TAB_COLUMNS Columns of user's tables, views and clusters
USER_TAB_COMMENTS Comments on the tables and views owned by the user
USER_TAB_GRANTS Grants on objects for which the user is the owner, grantor or grantee
USER_TAB_GRANTS_MADE All grants on objects owned by the user
USER_TAB_GRANTS_RECD Grants on objects for which the user is the grantee
USER_TAB_PRIVS Grants on objects for which the user is the owner, grantor or grantee
USER_TAB_PRIVS_MADE All grants on objects owned by the user
USER_TAB_PRIVS_RECD Grants on objects for which the user is the grantee
USER_TRIGGERS Triggers owned by the user
USER_TRIGGER_COLS Column usage in user's triggers
USER_TS_QUOTAS Tablespace quotas for the user
USER_USERS Information about the current user
USER_VIEWS Text of views owned by the user
AUDIT_ACTIONS Description table for audit trail action type codes. Maps action type numbers to action type names
COLUMN_PRIVILEGES Grants on columns for which the user is the grantor, grantee, owner, or an enabled role or PUBLIC is the grantee
DICTIONARY Description of data dictionary tables and views
DICT_COLUMNS Description of columns in data dictionary tables and views
DUAL  
GLOBAL_NAME global database name
INDEX_HISTOGRAM statistics on keys with repeat count
INDEX_STATS statistics on the b-tree
RESOURCE_COST Cost for each resource
ROLE_ROLE_PRIVS Roles which are granted to roles
ROLE_SYS_PRIVS System privileges granted to roles
ROLE_TAB_PRIVS Table privileges granted to roles
SESSION_PRIVS Privileges which the user currently has set
SESSION_ROLES Roles which the user currently has enabled.
TABLE_PRIVILEGES Grants on objects for which the user is the grantor, grantee, owner, or an enabled role or PUBLIC is the grantee
ACCESSIBLE_COLUMNS Synonym for ALL_TAB_COLUMNS
ALL_COL_GRANTS Synonym for COLUMN_PRIVILEGES
ALL_JOBS Synonym for USER_JOBS
ALL_TAB_GRANTS Synonym for TABLE_PRIVILEGES
CAT Synonym for USER_CATALOG
CLU Synonym for USER_CLUSTERS
COLS Synonym for USER_TAB_COLUMNS
DBA_AUDIT_CONNECT Synonym for USER_AUDIT_CONNECT
DBA_AUDIT_RESOURCE Synonym for USER_AUDIT_RESOURCE
DBA_REFRESH_CHILDREN Synonym for USER_REFRESH_CHILDREN
DICT Synonym for DICTIONARY
IND Synonym for USER_INDEXES
OBJ Synonym for USER_OBJECTS
SEQ Synonym for USER_SEQUENCES
SM$VERSION Synonym for SM_$VERSION
SYN Synonym for USER_SYNONYMS
TABS Synonym for USER_TABLES
V$ACCESS Synonym for V_$ACCESS
V$ARCHIVE Synonym for V_$ARCHIVE
V$BACKUP Synonym for V_$BACKUP
V$BGPROCESS Synonym for V_$BGPROCESS
V$CIRCUIT Synonym for V_$CIRCUIT
V$COMPATIBILITY Synonym for V_$COMPATIBILITY
V$COMPATSEG Synonym for V_$COMPATSEG
V$CONTROLFILE Synonym for V_$CONTROLFILE
V$DATABASE Synonym for V_$DATABASE
V$DATAFILE Synonym for V_$DATAFILE
V$DBFILE Synonym for V_$DBFILE
V$DBLINK Synonym for V_$DBLINK
V$DB_OBJECT_CACHE Synonym for V_$DB_OBJECT_CACHE
V$DISPATCHER Synonym for V_$DISPATCHER
V$ENABLEDPRIVS Synonym for V_$ENABLEDPRIVS
V$FILESTAT Synonym for V_$FILESTAT
V$FIXED_TABLE Synonym for V_$FIXED_TABLE
V$LATCH Synonym for V_$LATCH
V$LATCHHOLDER Synonym for V_$LATCHHOLDER
V$LATCHNAME Synonym for V_$LATCHNAME
V$LIBRARYCACHE Synonym for V_$LIBRARYCACHE
V$LICENSE Synonym for V_$LICENSE
V$LOADCSTAT Synonym for V_$LOADCSTAT
V$LOADTSTAT Synonym for V_$LOADTSTAT
V$LOCK Synonym for V_$LOCK
V$LOG Synonym for V_$LOG
V$LOGFILE Synonym for V_$LOGFILE
V$LOGHIST Synonym for V_$LOGHIST
V$LOG_HISTORY Synonym for V_$LOG_HISTORY
V$MLS_PARAMETERS Synonym for V_$MLS_PARAMETERS
V$MTS Synonym for V_$MTS
V$NLS_PARAMETERS Synonym for V_$NLS_PARAMETERS
V$NLS_VALID_VALUES Synonym for V_$NLS_VALID_VALUES
V$OPEN_CURSOR Synonym for V_$OPEN_CURSOR
V$OPTION Synonym for V_$OPTION
V$PARAMETER Synonym for V_$PARAMETER
V$PQ_SESSTAT Synonym for V_$PQ_SESSTAT
V$PQ_SLAVE Synonym for V_$PQ_SLAVE
V$PQ_SYSSTAT Synonym for V_$PQ_SYSSTAT
V$PROCESS Synonym for V_$PROCESS
V$QUEUE Synonym for V_$QUEUE
V$RECOVERY_LOG Synonym for V_$RECOVERY_LOG
V$RECOVER_FILE Synonym for V_$RECOVER_FILE
V$REQDIST Synonym for V_$REQDIST
V$RESOURCE Synonym for V_$RESOURCE
V$ROLLNAME Synonym for V_$ROLLNAME
V$ROLLSTAT Synonym for V_$ROLLSTAT
V$ROWCACHE Synonym for V_$ROWCACHE
V$SESSION Synonym for V_$SESSION
V$SESSION_CURSOR_CACHE Synonym for V_$SESSION_CURSOR_CACHE
V$SESSION_EVENT Synonym for V_$SESSION_EVENT
V$SESSION_WAIT Synonym for V_$SESSION_WAIT
V$SESSTAT Synonym for V_$SESSTAT
V$SESS_IO Synonym for V_$SESS_IO
V$SGA Synonym for V_$SGA
V$SGASTAT Synonym for V_$SGASTAT
V$SHARED_SERVER Synonym for V_$SHARED_SERVER
V$SQLAREA Synonym for V_$SQLAREA
V$STATNAME Synonym for V_$STATNAME
V$SYSSTAT Synonym for V_$SYSSTAT
V$SYSTEM_CURSOR_CACHE Synonym for V_$SYSTEM_CURSOR_CACHE
V$SYSTEM_EVENT Synonym for V_$SYSTEM_EVENT
V$THREAD Synonym for V_$THREAD
V$TIMER Synonym for V_$TIMER
V$TRANSACTION Synonym for V_$TRANSACTION
V$TYPE_SIZE Synonym for V_$TYPE_SIZE
V$VERSION Synonym for V_$VERSION
V$WAITSTAT Synonym for V_$WAITSTAT
V$_LOCK Synonym for V_$_LOCK

在Oracle中实现数据库的复制

在Internet上运作数据库经常会有这样的需求:把遍布全国各城市相似的数据库应用统一起来,一个节点的数据改变不仅体现在本地,还反映到远端。复制技术给用户提供了一种快速访问共享数据的办法。
一、实现数据库复制的前提条件
1、数据库支持高级复制功能
您可以用system身份登录数据库,查看v$option视图,如果其中Advanced replication为TRUE,则支持高级复制功能;否则不支持。
2、数据库初始化参数要求
①、db_domain = test.com.cn
指明数据库的域名(默认的是WORLD),这里可以用您公司的域名。
②、global_names = true
它要求数据库链接(database link)和被连接的数据库名称一致。
现在全局数据库名:db_name+”.”+db_domain
③、有跟数据库job执行有关的参数
job_queue_processes = 1
job_queue_interval = 60
distributed_transactions = 10
open_links = 4
第一行定义SNP进程的启动个数为n。系统缺省值为0,正常定义范围为0~36,根据任务的多少,可以配置不同的数值。
第二行定义系统每隔N秒唤醒该进程一次。系统缺省值为60秒,正常范围为1~3600秒。事实上,该进程执行完当前任务后,就进入睡眠状态,睡眠一段时间后,由系统的总控负责将其唤醒。
如果修改了以上这几个参数,需要重新启动数据库以使参数生效。
二、实现数据库同步复制的步骤
假设在Internet上我们有两个数据库:一个叫深圳(shenzhen),一个叫北京(beijing)。
具体配置见下表:
数据库名 shenzhen beijing
数据库域名 test.com.cn test.com.cn
数据库sid号 shenzhen beijing
Listener端口号 1521 1521
服务器ip地址 10.1.1.100 10.1.1.200

1、确认两台数据库之间可以互相访问,在tnsnames.ora里设置数据库连接字符串。
①、例如:深圳这边的数据库连接字符串是以下的格式
beijing =
(DESCRIPTION =
(ADDRESS_LIST =
(ADDRESS = (PROTOCOL = TCP)(HOST = 10.1.1.200)(PORT = 1521))
)
(CONNECT_DATA =
(SERVICE_NAME = beijing)
)
)
运行$tnsping beijing
出现以下提示符:
Attempting to contact (ADDRESS=(PROTOCOL=TCP)(HOST=10.1.1.200)(PORT=1521))
OK(n毫秒)
表明深圳数据库可以访问北京数据库。
②、在北京那边也同样配置,确认$tnsping shenzhen 是通的。
2、改数据库全局名称,建公共的数据库链接。
①、用system身份登录shenzhen数据库
SQL>alter database rename global_name to shenzhen.test.com.cn;
用system身份登录beijing数据库:
SQL>alter database rename global_name to beijing.test.com.cn;
②、用system身份登录shenzhen数据库
SQL>create public database link beijing.test.com.cn using 'beijing';
测试数据库全局名称和公共的数据库链接
SQL>select * from global_name@beijing.test.com.cn;
返回结果为beijing.test.com.cn就对了。
用system身份登录beijing数据库:
SQL>create public database link shenzhen.test.com.cn using 'shenzhen';
测试数据库全局名称和公共的数据库链接
SQL>select * from global_name@shenzhen.test.com.cn;
返回结果为shenzhen.test.com.cn就对了。
3、建立管理数据库复制的用户repadmin,并赋权。
①、用system身份登录shenzhen数据库
SQL>create user repadmin identified by repadmin default tablespace users temporary tablespace temp;
SQL>execute dbms_defer_sys.register_propagator('repadmin');
SQL>grant execute any procedure to repadmin;
SQL>execute dbms_repcat_admin.grant_admin_any_repgroup('repadmin');
SQL>grant comment any table to repadmin;
SQL>grant lock any table to repadmin;
②、同样用system身份登录beijing数据库,运行以上的命令,管理数据库复制的用户repadmin,并赋权。
说明:repadmin用户名和密码可以根据用户的需求自由命名。
4、在数据库复制的用户repadmin下创建私有的数据库链接。
①、用repadmin身份登录shenzhen数据库
SQL>create database link beijing.test.com.cn connect to repadmin identified by repadmin;
测试这个私有的数据库链接:
SQL>select * from global_name@beijing.test.com.cn;
返回结果为beijing.test.com.cn就对了。
②、用repadmin身份登录beijing数据库
SQL>create database link shenzhen.test.com.cn connect to repadmin identified by repadmin;
测试这个私有的数据库链接
SQL>select * from global_name@shenzhen.test.com.cn;
返回结果为shenzhen.test.com.cn就对了。
5、创建或选择实现数据库复制的用户和对象,给用户赋权,数据库对象必须有主关键字。
假设我们用ORACLE里举例用的scott用户,dept表。
①、用internal身份登录shenzhen数据库,创建scott用户并赋权
SQL>create user scott identified by tiger default tablespace users temporary tablespace temp;
SQL>grant connect, resource to scott;
SQL>grant execute on sys.dbms_defer to scott;
②、用scott身份登录shenzhen数据库,创建表dept
SQL>create table dept
(deptno number(2) primary key,
dname varchar2(14),
loc varchar2(13) );
③、如果数据库对象没有主关键字,可以运行以下SQL命令添加:
SQL>alter table dept add (constraint dept_deptno_pk primary key (deptno));
④、在shenzhen数据库scott用户下创建主关键字的序列号,范围避免和beijing的冲突。
SQL> create sequence dept_no increment by 1 start with 1 maxvalue 44 cycle nocache;
(说明:maxvalue 44可以根据应用程序及表结构主关键字定义的位数需要而定)
⑤、在shenzhen数据库scott用户下插入初始化数据
SQL>insert into dept values (dept_no.nextval,'accounting','new york');
SQL>insert into dept values (dept_no.nextval,'research','dallas');
SQL>commit;
⑥、在beijing数据库那边同样运行以上①,②,③
⑦、在beijing数据库scott用户下创建主关键字的序列号,范围避免和shenzhen的冲突。
SQL> create sequence dept_no increment by 1 start with 45 maxvalue 99 cycle nocache;
⑧、在beijing数据库scott用户下插入初始化数据
SQL>insert into dept values (dept_no.nextval,'sales','chicago');
SQL>insert into dept values (dept_no.nextval,'operations','boston');
SQL>commit;
6、创建要复制的组scott_mg,加入数据库对象,产生对象的复制支持
①、用repadmin身份登录shenzhen数据库,创建主复制组scott_mg
SQL> execute dbms_repcat.create_master_repgroup('scott_mg');
说明:scott_mg组名可以根据用户的需求自由命名。
②、在复制组scott_mg里加入数据库对象
SQL>execute dbms_repcat.create_master_repobject(sname=>'scott',oname=>'dept', type=>'table',use_existing_object=>true,gname=>'scott_mg');
参数说明:
sname 实现数据库复制的用户名称
oname 实现数据库复制的数据库对象名称
(表名长度在27个字节内,程序包名长度在24个字节内)
type 实现数据库复制的数据库对象类别
(支持的类别:表,索引,同义词,触发器,视图,过程,函数,程序包,程序包体)
use_existing_object true表示用主复制节点已经存在的数据库对象
gname 主复制组名
③、对数据库对象产生复制支持
SQL>execute dbms_repcat.generate_replication_support('scott','dept','table');
(说明:产生支持scott用户下dept表复制的数据库触发器和程序包)
④、确认复制的组和对象已经加入数据库的数据字典
SQL>select gname, master, status from dba_repgroup;
SQL>select * from dba_repobject;
7、创建主复制节点
①、用repadmin身份登录shenzhen数据库,创建主复制节点
SQL>execute dbms_repcat.add_master_database
(gname=>'scott_mg',master=>'beijing.test.com.cn',use_existing_objects=>true, copy_rows=>false, propagation_mode => 'asynchronous');
参数说明:
gname 主复制组名
master 加入主复制节点的另一个数据库
use_existing_object true表示用主复制节点已经存在的数据库对象
copy_rows false表示第一次开始复制时不用和主复制节点保持一致
propagation_mode 异步地执行
②、确认复制的任务队列已经加入数据库的数据字典
SQL>select * from user_jobs;
8、使同步组的状态由停顿(quiesced )改为正常(normal)
①、用repadmin身份登录shenzhen数据库,运行以下命令
SQL> execute dbms_repcat.resume_master_activity('scott_mg',false);
②、确认同步组的状态为正常(normal)
SQL> select gname, master, status from dba_repgroup;
③、如果这个①命令不能使同步组的状态为正常(normal),可能有一些停顿的复制,运行以下命令再试试(建议在紧急的时候才用):
SQL> execute dbms_repcat.resume_master_activity('scott_mg',true);
9、创建复制数据库的时间表,我们假设用固定的时间表:10分钟复制一次。
①、用repadmin身份登录shenzhen数据库,运行以下命令
SQL>begin
dbms_defer_sys.schedule_push (
destination => 'beijing.test.com.cn',
interval => 'sysdate + 10/1440',
next_date => sysdate);
end;
/

SQL>begin
dbms_defer_sys.schedule_purge (
next_date => sysdate,
interval => 'sysdate + 10/1440',
delay_seconds => 0,
rollback_segment => '');
end;
/

②、用repadmin身份登录beijing数据库,运行以下命令
SQL>begin
dbms_defer_sys.schedule_push (
destination => ' shenzhen.test.com.cn ',
interval => 'sysdate + 10 / 1440',
next_date => sysdate);
end;
/

SQL>begin
dbms_defer_sys.schedule_purge (
next_date => sysdate,
interval => 'sysdate + 10/1440',
delay_seconds => 0,
rollback_segment => '');
end;
/
10、添加或修改两边数据库的记录,跟踪复制过程
如果你想立刻看到添加或修改后数据库的记录的变化,可以在两边repadmin用户下找到push的job_number,然后运行:
SQL>exec dbms_job.run(job_number);
三、异常情况的处理
1、检查复制工作正常否,可以在repadmin 用户下查询user_jobs
SQL>select job,this_date,next_date,what, broken from user_jobs;
正常的状态有两种:
任务闲——this_date为空,next_date为当前时间后的一个时间值
任务忙——this_date不为空,next_date为当前时间后的一个时间值
异常状态也有两种:
任务死锁——next_date为当前时间前的一个时间值
任务死锁——next_date为非常大的一个时间值,例如:4001-01-01
这可能因为网络中断照成的死锁
解除死锁的办法:
$ps –ef|grep orale
找到死锁的刷新快照的进程号ora_snp*,用kill –9 命令删除此进程
然后进入repadmin 用户SQL>操作符下,运行命令:
SQL>exec dbms_job.run(job_number);
说明:job_number 为用select job,this_date,next_date,what from user_jobs;命令查出的job编号。
2、增加或减少复制组的复制对象
①、停止主数据库节点的复制动作,使同步组的状态由正常(normal)改为停顿(quiesced )
用repadmin身份登录shenzhen数据库,运行以下命令
SQL>execute dbms_repcat.suspend_master_activity (gname => 'scott_mg');
②、在复制组scott_mg里加入数据库对象,保证数据库对象必须有主关键字。
SQL>execute dbms_repcat.create_master_repobject(sname=>'scott',oname=>'emp', type=>'table',use_existing_object=>true,gname=>'scott_mg');
对加入的数据库对象产生复制支持
SQL>execute dbms_repcat.generate_replication_support('scott','emp','table');
③、在复制组scott_mg里删除数据库对象。
SQL>execute dbms_repcat.drop_master_repobject ('scott','dept','table');
④、重新使同步组的状态由停顿(quiesced )改为正常(normal)。
SQL> execute dbms_repcat.resume_master_activity('scott_mg',false);

SQL*PLUS环境输入'&字符'的方法

我们知道在SQL*PLUS默认环境里会把'&字符'当成变量来处理.

有些时候我们也需要在SQL>的符号下输入'&字符', 只需要改变SQL*PLUS下一个环境变量define即可.

   SQL> set define off;

是把默认的&绑定变量的功能取消, 可以把'&字符'当成普通字符处理

SQL> set define on;

打开&绑定变量的功能, &后面的字符串当变量使用.

SQL> show define;

查看当前SQL*PLUS的define状态

举例说明:
---------------------------------------------------------------
SQL> CREATE TABLE TEST3 (
ID NUMBER (2) PRIMARY KEY,
NAME VARCHAR2 (20));

SQL> show define;
define "&" (hex 26)

SQL> insert into test3 values(1,'sgs&a&n');
Enter value for a: abc
Enter value for n: 456
old 1: insert into test3 values(1,'sgs&a&n')
new 1: insert into test3 values(1,'sgsabc456')

1 row created.

SQL> commit;

Commit complete.

SQL> set define off;

SQL> insert into test3 values(2,'sgs&a&n');

1 row created.

SQL> commit;

Commit complete.

SQL> select * from test3;

ID NAME
-- --------------------
1 sgsabc456
2 sgs&a&n

简说创建用户

SQL>create user dbuser identified by oracle default tablespace data temporary tablespace temp quota unlimited on data quota 0 on system quota 0 on tools quota 0 on users;
SQL>grant connect to dbuser;
SQL>grant create procedure to dbuser; #这些权限足够用于开发及生产环境
SQL>grant select on dba_pending_transactions to dbuser; #二阶段提交过程中类似Tuxedo的软件需要检索挂起交易的状态,所以必须得到对此视图的select权限,以sys用户身份赋予
修改用户可使用alter user dbuser ...
参考命令:
drop user dbuser cascade; #删除用户及其所有的数据对象
revoke connect from dbuser; #取消用户角色权限
相关系统表:
user(dba)_users
user(dba)_role_privs 角色权限
user(dba)_sys_privs 系统权限
user(dba)_tab_privs 对其它用户表操作的权限
user_ts_quotas 表空间限额

创建只读用户
假定数据库用户dbbrsr需要对dbuser的表emp拥有select权力
connect dbuser
grant select on emp to dbbrsr
connect dbbrsr
create synonym emp for dbuser.emp;
这样,dbbrsr就能象使用自己的表一样对dbuser的表执行select操作

简说Oracle启动及关闭数据库实例

oracle用户,dbstart和dbshut启动及关闭/var/opt/oracle/oratab或/etc/oratab中设定的数据库实例,dbstart采用normal方式,dbshut采用immediate方式。
或者使用手工方式
sqlplus “/ as sysdba”
启动
normal
SQL>startup
mount
SQL>startup mount; #启动实例进程,载入数据库文件,允许DBA权限的某些操作,但禁止对数据库文件的一般性操作
SQL>完成某些操作
SQL>alter database open;
nomount
SQL>startup nomount; #启动实例进程,但不允许访问数据库,常用于创建数据库、介质恢复或创建controlfile
SQL>完成某些操作
SQL>alter database open;
关闭
normal
SQL>shutdown或SQL>shutdown transactional; #等待每个连接交易完成后,切断连接,再关闭数据库
immediate
SQL>shutdown immediate; #立刻中止每个连接,交易回滚
abort
SQL>shutdown abort; #立刻关闭数据库,不保证交易完整性,在下一次启动打开数据库文件时会进行介质恢复

简说Oracle数据库导出(exp)/导入(imp)

exp
将数据库内的各对象以二进制方式下载成dmp文件,方便数据迁移。
buffer:下载数据缓冲区,以字节为单位,缺省依赖操作系统
consistent:下载期间所涉及的数据保持read only,缺省为n
direct:使用直通方式 ,缺省为n
feeback:显示处理记录条数,缺省为0,即不显示
file:输出文件,缺省为expdat.dmp
filesize:输出文件大小,缺省为操作系统最大值
indexes:是否下载索引,缺省为n,这是指索引的定义而非数据,exp不下载索引数据
log:log文件,缺省为无,在标准输出显示
owner:指明下载的用户名
query:选择记录的一个子集
rows:是否下载表记录
tables:输出的表名列表
导出整个实例
exp dbuser/oracle file=oradb.dmp log=oradb.log full=y consistent=y direct=y
user应具有dba权限
导出某个用户所有对象
exp dbuser/oracle file=dbuser.dmp log=dbuser.log owner=dbuser buffer=4096000 feedback=10000
导出一张或几张表
exp dbuser/oracle file=dbuser.dmp log=dbuser.log tables=table1,table2 buffer=4096000 feedback=10000
导出某张表的部分数据
exp dbuser/oracle file=dbuser.dmp log=dbuser.log tables=table1 buffer=4096000 feedback=10000 query=\”where col1=\’…\’ and col2 \<…\”
不可用于嵌套表
以多个固定大小文件方式导出某张表
exp dbuser/oracle file=1.dmp,2.dmp,3.dmp,… filesize=1000m tables=emp buffer=4096000 feedback=10000
这种做法通常用在:表数据量较大,单个dump文件可能会超出文件系统的限制
直通路径方式
direct=y,取代buffer选项,query选项不可用
有利于提高下载速度
consistent选项
自export启动后,consistent=y冻结来自其它会话的对export操作的数据对象的更新,这样可以保证dump结果的一致性。但这个过程不能太长,以免回滚段和联机日志消耗完
imp
将exp下载的dmp文件上载到数据库内。
buffer:上载数据缓冲区,以字节为单位,缺省依赖操作系统
commit:上载数据缓冲区中的记录上载后是否执行提交
feeback:显示处理记录条数,缺省为0,即不显示
file:输入文件,缺省为expdat.dmp
filesize:输入文件大小,缺省为操作系统最大值
fromuser:指明来源用户方
ignore:是否忽略对象创建错误,缺省为n,在上载前对象已被建立往往是一个正常现象,所以此选项建议设为y
indexes:是否上载索引,缺省为n,这是指索引的定义而非数据,如果上载时索引已建立,此选项即使为n也无效,imp自动更新索引数据
log:log文件,缺省为无,在标准输出显示
rows:是否上载表记录
tables:输入的表名列表
touser:指明目的用户方
导入整个实例
imp dbuser/oracle file=oradb.dmp log=oradb.log full=y buffer=4096000 commit=y ignore=y feedback=10000
导入某个用户所有对象
imp dbuser/oracle file=dbuser.dmp log=dbuser.log fromuser=dbuser touser=dbuser2 buffer=2048000 commit=y ignore=y feedback=10000
导入一张或几张表
imp dbuser2/oracle file=user.dmp log=user.log tables=table1,table2 fromuser=dbuser touser=dbuser2 buffer=2048000 commit=y ignore=y feedback=10000
以多个固定大小文件方式导入某张表
imp dbuser/oracle file=\(1.dmp,2.dmp,3.dmp,…\) filesize=1000m tables=emp fromuser=dbuser touser=dbuser2 buffer=4096000 commit=y ignore=y feedback=10000


如何修改internal的口令?

转自oracle技术网 阿木伯 着
========================================
软件环境:
1、Windows NT4.0+ORACLE 8.0.4
2、ORACLE安装路径为:C:\ORANT

实现方法:
用法:orapwd file= password= entries=

参数解释:
    file - name of password file (mand),
    password - password for SYS and INTERNAL (mand),
    entries - maximum number of distinct DBA and OPERs (opt),
    There are no spaces around the equal-to (=) character.

1、进入DOS下

2、默认internal密码文件在c:\orant\database下,是隐藏属性,文件名称与数据库实例名有关

  如默认ORACLE实例名为ORCL,则internal密码文件名为pwdorcl.ora

3、建立新的internal密码文件,起个新名字为pwdora8.ora

  orapwd80 file=pwdora8.ora password=B entries=5     --注:password项一定要用大写,并且不要用单引号

4、拷贝pwdora8.ora文件到c:\orant\database目录下

5、运行regedit,修改口令文件指向

6、找到HKEY_LOCAL_MACHINE\SOFTWARE\ORACLE项

  定位ORA_ORCL_PWFILE子项,改变其值为c:\orant\database\pwdora8.ora

7、关闭ORACLE数据库,重新启动

8、进入svrmgr30服务程序,测试internal密码是否更改成功

PB绝对有用的未公开函数

已知一个DW中的某列的列名(在字符串变量中),以获得这个列对象的DWO
方法是:
DWObject ldwo_use,ldwo_name
ldwo_use = dw_1.Object
ldwo_name = ldwo_use.__get_attribute("name",FALSE)
这样就可以在用setitem()设置值时,手工调用数窗的itemchanged事件,校验是否接受该值
int li_rtn
li_rtn = dw_1.event itemchanged(dw_1.GetROW(),ldwo_name,'arg1')
if li_rtn = 0 then
dw_1.SetItem(dw_1.GetROW(),'name",'arg1')
end if
非复合报表中的嵌套报表不可使用getchild取得,也不可使用describe取得属性和使用modify更改属性,
你可以调用PB未载入文档的函数来获取/更改属性,请看示例,注意多层嵌套时使用循环获取最终对象.

例:数据窗口控件dw_test包含嵌套报表dw_1,dw_1有栏位dept_name.
dwobject ldwo_parent,ldwo_obj
string ls_color
ldwo_parent = dw_1.o b j e c t
ldwo_obj = ldwo_parent.__get_attribute("dw_1",false)
ldwo_obj = ldwo_obj.o b j e c t
ldwo_obj = ldwo_obj.__get_attribute("dept_name",false)
ls_color = ldwo_obj.color//取颜色
ldwo_obj.__set_attribute("color",rgb(192,192,192))//更改颜色
__get_attribute()、__get_attribute_item()、__invoke_method()、__set_attribute()、__set_attribute_item()

pb 数据导出到excel 中的程序

pb 数据导出到excel 中的程序
鉴于现在很多朋友询问 pb 数据导出到excel 中的问题,导出去后格式和数据
类型不对了,自己写了几个用户对象,
希望能抛砖引玉,加强技术交流,得到大家的支持。

1. nvo_excel 只要是两个接口函数
导出数据存储的数据,可以定义 excel 的标题
public function integer uf_toexcel (datastore ads_data, readonly string as_title)

导出数据窗口的数据,可以定义 excel 的标题
public function integer uf_toexcel (datawindow adw_data, readonly string as_title)

2. 下面是两个用户对象的 sru 文件,自己导入到工程中
$PBExportHeader$uo_ds_base.sru
$PBExportComments$数据存储基类
forward
global type uo_ds_base from datastore
end type
end forward

global type uo_ds_base from datastore
string dataobject = "d_expression"
end type
global uo_ds_base uo_ds_base

forward prototypes
public function any uf_getitemvalue (long al_row, string as_colname)
public function string uf_about ()
public function string uf_globalreplace (string as_source, string as_old, string as_new)
end prototypes

public function any uf_getitemvalue (long al_row, string as_colname);
//*************************************************//
//function : 得到任意的列的值
//parm :
// 1. al_row : 指定行
// 2. as_colname : 指定列的列名
//return : -1 is fail or success is value to you
//author : hzh
//date : 2002.11.05
//************************************************//

String s_tempcoltype
any a_ret
s_tempcoltype = Lower(THIS.Describe(as_colname + ".coltype"))

//for string type
IF Left(s_tempcoltype,4) = "char" OR Left(s_tempcoltype,4) ="varc"then
a_ret = THIS.GetItemString(al_row,as_colname)
END IF

//for decimal type
IF Left(s_tempcoltype,7) = "decimal" then
a_ret = THIS.GetItemDecimal(al_row,as_colname)
END IF

//for date type
IF s_tempcoltype = "date" THEN
a_ret = THIS.GetItemDate(al_row,as_colname)
END IF

//for datetime type
IF s_tempcoltype = "datetime" THEN
a_ret = THIS.GetItemDateTime(al_row,as_colname)
END IF

//for number type
IF s_tempcoltype = "number" THEN
a_ret = THIS.GetItemNumber(al_row,as_colname)
END IF

//for time type
IF s_tempcoltype = "time" THEN
a_ret = THIS.GetItemTime(al_row,as_colname)
END IF

//for timestamp type
IF s_tempcoltype = "timestamp" THEN
a_ret = THIS.GetItemTime(al_row,as_colname)
END IF

//for int or long
IF s_tempcoltype = "int" OR s_tempcoltype = "long" THEN
a_ret = THIS.GetItemnumber(al_row,as_colname)
END IF

IF IsNull(a_ret) THEN
RETURN -1
END IF

RETURN a_ret

end function

public function string uf_about ();
string s_func = ""

s_func = " 1. 求得表达式的值 (uf_evaluate) " +&
" 2. 根据 SQL ,创建数据存储 (uf_setsqlselect) ~r~n " +&
" 3. 得到任意列的值(uf_getitemvalue) ~r~n "

//s_func += SUPER :: uf_about()


RETURN "uo_ds_base object member's functions : ~r~n" + s_func


end function
public function string uf_globalreplace (string as_source, string as_old, string as_new);
//**************************************************************//
//function : 用指定的字符串替换指定字符串
//parm :
// 1. as_source : 原来的字符串
// 2. as_old : 将要被替换的字符串
// 3. as_new : 用来替换的字符串
//return : 新的字符串
//author : hzh
//date : 2002.11.14
//*************************************************************//

Long l_newlen, l_oldlen, l_start
String s_null, s_source


IF IsNull(as_source) OR IsNull(as_old) OR IsNull(as_new) THEN
SetNull(s_null)
RETURN s_null
ELSE
l_oldlen = Len(as_old)
l_newlen = Len(as_new)
as_Old = Lower(as_old)
s_Source = Lower(as_source)
END IF

l_start = Pos(s_source, as_old)

DO WHILE l_start > 0
as_source = Replace(as_source, l_start, l_oldlen, as_new)
s_source = Lower(as_Source)
l_start = Pos(s_source, as_old, (l_start + l_newlen))
LOOP


RETURN as_source

end function
on uo_ds_base.create
call super::create
TriggerEvent( this, "constructor" )
end on

on uo_ds_base.destroy
TriggerEvent( this, "destructor" )
call super::destroy
end on





hzhxxx(程序方程) 于 2004-9-1 10:38:11

$PBExportHeader$nvo_excel.sru
$PBExportComments$和 excel 通讯的功能函数
forward
global type nvo_excel from nonvisualobject
end type
end forward

global type nvo_excel from nonvisualobject
end type
global nvo_excel nvo_excel

type prototypes
Private:
Function uint GetModuleFileNameA(ulong hModule,ref string lpFilename,ulong nSize) Library "kernel32.dll"
end prototypes

type variables

Private:
//存储要导出的数据
uo_ds_base ids_data

//列名
String is_columnname[]

//列的标题
String is_columntitle[]

//列的显示格式
String is_columnformat[]

//列的类型
String is_columntype[]
end variables

forward prototypes
public function integer uf_toexcel (datastore ads_data, readonly string as_title)
public function integer uf_toexcel (datawindow adw_data, readonly string as_title)
private function integer uf_setdatasource (datawindow adw_data)
private function integer uf_setdatasource (datastore ads_data)
private function integer uf_datatoexcel (string as_title)
public function string uf_about ()
private function integer uf_initcolumn ()
end prototypes

public function integer uf_toexcel (datastore ads_data, readonly string as_title);

/**********************************************************/
//Function : 转换数据到 excel
//parm :
// 1. ads_data : 包含源数据的对象
// 2. as_title : excel 的标题
//return : 1 is success and -1 is fail
//Author : hzh
//date : 2003.12.08
/**********************************************************/

IF THIS.uf_setdatasource(ads_data) <> 1 THEN RETURN -1

IF NOT IsValid(ids_data) THEN RETURN -1

IF ids_data.RowCount() < 1 THEN RETURN -1

THIS.uf_initcolumn()

THIS.uf_datatoexcel(as_title)


RETURN 1
end function

public function integer uf_toexcel (datawindow adw_data, readonly string as_title);
/**********************************************************/
//Function : 转换数据到 excel
//parm :
// 1. adw_data : 包含源数据的对象
// 2. as_title : excel 的标题
//return : 1 is success and -1 is fail
//Author : hzh
//date : 2003.12.08
/**********************************************************/

IF THIS.uf_setdatasource(adw_data) <> 1 THEN RETURN -1

IF NOT IsValid(ids_data) THEN RETURN -1

IF ids_data.RowCount() < 1 THEN RETURN -1


THIS.uf_initcolumn()

THIS.uf_datatoexcel(as_title)

RETURN 1
end function

private function integer uf_setdatasource (datawindow adw_data);/**********************************************************/
//Function : 设置数据存储
//parm : None
//return :
//Author : hzh
//date : 2003.12.08
/**********************************************************/


ids_data.dataobject = adw_data.dataobject
//ids_data.uf_setddobject()
RETURN adw_data.ShareData(ids_data)



end function

private function integer uf_setdatasource (datastore ads_data);
/**********************************************************/
//Function : 设置数据存储
//parm : None
//return :
//Author : hzh
//date : 2003.12.08
/**********************************************************/

ids_data.dataobject = ads_data.dataobject
//ids_data.uf_setddobject()
RETURN ads_data.ShareData(ids_data)
end function

private function integer uf_datatoexcel (string as_title);
/**********************************************************/
//Function : 转换数据到 excel
//parm :
// 1. as_title : excel 的标题
//return : 1 is success and -1 is fail
//Author : hzh
//date : 2003.12.08
//Modifier :
// 1. 2003.12.10 by hzh
//Reason :
// 1. 增加对计算列的处理
/**********************************************************/

long l_cnt,l_i,l_cols,l_rows

string s_colnum ,s_colname,s_range

OLEObject xlapp , xlsub

//l_cols = long(ids_data.Object.DataWindow.Column.Count)
l_cols = UpperBound(is_columntitle)


l_rows = ids_data.RowCount()

IF NOT IsValid(xlApp) THEN
xlApp = CREATE OLEObject
END IF

IF xlApp.ConnectToNewObject( "Excel.Application" ) < 0 THEN
MessageBox('ga_app.dwmessagetitle',"不能连接 EXCEL 服务器,请检查你的计算机中是 ~r~n " +&
"否安装了MS EXCEL ? 假如安装,请与程序供应商联系 !",QuesTion!)
RETURN -1
END IF

//增加空文档 (EXCEL table)
xlApp.Application.Workbooks.add()
xlApp.Application.Visible = TRUE

IF NOT IsValid(xlsub) THEN
xlsub = CREATE OLEObject
END IF

//定位到第一格
xlsub = xlapp.Application.ActiveWorkbook.Worksheets[1]

//取得最后列的字母表达式
IF Long(l_cols) > 26 then
//AA、AB...还是BA、BB、BC...
int i_colstart,i_colend
i_colstart = Mod(l_cols,26)
i_colend = l_cols / 26
s_colnum = "'" + Char(i_colstart + 96 ) + Char(i_colend + 96) + "'"
ELSE
//是 A,B,C...格式
s_colnum = char(l_cols + 96)
END IF

//标题的设置
xlsub.cells[1,1] = as_title
xlsub.cells[1,1].HorizontalAlignment = 3
xlsub.cells[1,1].VerticalAlignment = 3
xlsub.cells[1,1].Font.Size = 18


//去处格子
xlsub.range("A1:" + s_colnum + "1").Merge()

FOR l_i = 1 TO l_cols
//设置标题列的名字
xlsub.cells[2,l_i] = is_columntitle[l_i]
NEXT

//画表格线
//数据行从第二行开始
s_range = "A2:" + s_colnum + Trim(String(l_rows + 2))
xlsub.range(s_range).borders(1).linestyle = 1
xlsub.range(s_range).borders(2).linestyle = 1
xlsub.range(s_range).borders(3).linestyle = 1
xlsub.range(s_range).borders(4).linestyle = 1

//将数据写到EXECL
FOR l_i = 1 TO l_cols
FOR l_cnt = 1 TO l_rows
IF is_columntype[l_i] = 'column' THEN
String s_evaluate
s_evaluate = "Evaluate('LookUpDisplay(" + is_columnname[l_i]
s_evaluate += ")'," + String(l_cnt) + ')'
xlsub.cells[l_cnt + 2,l_i].FormulaR1C1 = ids_data.Describe(s_evaluate)
ELSE
xlsub.cells[l_cnt + 2,l_i].FormulaR1C1 = &
ids_data.uf_getitemvalue(l_cnt,is_columnname[l_i])
END IF
xlsub.cells[l_cnt + 2,l_i].NumberFormatLocal = is_columnformat[l_i]
NEXT
NEXT

xlapp.Application.ActiveWorkbook.saved = FALSE

xlApp.DisConnectObject()

IF IsValid(xlApp) THEN
DESTROY xlapp
END IF

IF IsValid(xlsub) THEN
DESTROY xlsub
END IF

RETURN 1
end function

public function string uf_about ();

/**********************************************************/
//Function : 用户对象功能介绍
//parm : None
//return : 介绍的文本和对应的公共函数
//Author : hzh
//date : 2003.12.08
/**********************************************************/


String s_func = ""

//s_func = super :: uf_about()

s_func = s_func + "~r~nvo_excel object member's functions : ~r~n"

s_func+= " 1. 用户对象功能介绍 (uf_about) ~r~n" +&
" 2. 程序数据导出为 excel 表,已经重载 (uf_toexcel) ~r~n"


RETURN s_func

end function
private function integer uf_initcolumn ();
/**********************************************************/
//Function : 初始化列信息
//parm :
//return : of no use
//Author : hzh
//date : 2003.12.08
//Modifier :
// 1. 2003.12.10 by hzh
//Reason :
// 1. 增加对计算列的处理
/**********************************************************/

Int i_cnt
String s_colname,s_datatype


//清空对象
FOR i_cnt = 1 TO UpperBound(is_columnname)
SetNull(is_columnname[i_cnt])
SetNull(is_columntitle[i_cnt])
SetNull(is_columnformat[i_cnt])
SetNull(is_columntype[i_cnt])
END FOR

String s_objects
uo_ds_base ds_excel
IF NOT IsValid(ds_excel) THEN
ds_excel = CREATE uo_ds_base
END IF

ds_excel.dataobject = 'dw_excel_columns'
s_objects = ids_data.Describe("DataWindow.Objects")

// 将 DETAIL 区域内的所有可见目标放到 ds_excel 中,
// 并按照 object.x 属性大小排序
DO WHILE Len(s_objects) > 0
Int i_pos
Long l_x
String s_name,s_type,s_band,s_visible,s_objtype
String s_objzw,s_zw

i_pos = Pos(s_objects, "~t")
IF i_pos <= 0 THEN i_pos = Len(s_objects) + 1
// Object 名字
s_name = Left(s_objects,i_pos - 1)
s_objects = Mid(s_objects,i_pos + 1, Len(s_objects))
//Object 数据类型
s_type = Lower(ids_data.Describe(s_name + ".coltype"))

// Object X 坐标
l_x = Long(ids_data.Describe(s_name + ".x"))
// Object 所属区域
s_band = Lower(ids_data.Describe(s_name + ".band"))
// Object 是否可见
s_visible = ids_data.Describe(s_name + ".visible")
// Object 类别
s_objtype = Lower(ids_data.Describe(s_name + ".type"))
// 如果 object 在 Detail 区,且可见,并且是 column 或 Compute Column
IF s_band = "detail" AND s_visible = "1" AND &
(s_objtype = "column" OR s_objtype = "compute" ) THEN

// Object 中文标头,支持标准命名
s_objzw = s_name + "_t"
s_zw = ids_data.describe(s_objzw + ".text")
// 去掉标题中多余的换行符,空格和引号
s_zw = ds_excel.uf_globalreplace(s_zw,"~n","")
s_zw = ds_excel.uf_globalreplace(s_zw," ","")
s_zw = ds_excel.uf_globalreplace(s_zw,'"',"")
Long l_newrow
l_newrow = ds_excel.InsertRow(0)
ds_excel.SetItem(l_newrow, "colname",s_name)
ds_excel.SetItem(l_newrow, "x",l_x)
ds_excel.SetItem(l_newrow, "coltype",s_type)
ds_excel.SetItem(l_newrow, "coltitle",s_zw)
ds_excel.SetItem(l_newrow, "objtype",s_objtype)
END IF
LOOP
//排序,设置到列数组中
ds_excel.SetSort("x a")
ds_excel.Sort()

FOR i_cnt = 1 TO ds_excel.RowCount()
is_columnname[i_cnt] = Lower(ds_excel.GetItemString(i_cnt,'colname'))
is_columntitle[i_cnt] = ds_excel.GetItemString(i_cnt,'coltitle')
is_columntype[i_cnt] = ds_excel.GetItemString(i_cnt,'objtype')
s_datatype = Left(Lower(ds_excel.GetItemString(i_cnt,'coltype')),4)
CHOOSE CASE s_datatype
CASE 'char','varc','int','long'
is_columnformat[i_cnt] = 'G/通用格式'

//特别指定日期专用格式为 char(10)
s_datatype = Lower(ds_excel.GetItemString(i_cnt,'coltype'))
IF s_datatype = 'char(10)' THEN
is_columnformat[i_cnt] = 'yyyy""年""m""月""d""日""'
END IF
CASE 'deci'
is_columnformat[i_cnt] = "0.00_ "
CASE 'date','datetime'
is_columnformat[i_cnt] = 'yyyy""年""m""月""d""日""'
CASE 'time'
is_columnformat[i_cnt] = 'h""时""mm""分""ss""秒""'
CASE ELSE
is_columnformat[i_cnt] = 'G/通用格式'
END CHOOSE
NEXT


IF IsValid(ds_excel) THEN
DESTROY ds_excel
END IF

RETURN 1

end function
on nvo_excel.create
call super::create
TriggerEvent( this, "constructor" )
end on

on nvo_excel.destroy
TriggerEvent( this, "destructor" )
call super::destroy
end on

event constructor;
IF NOT IsValid(ids_data) THEN
ids_data = CREATE uo_ds_base
END IF
end event

event destructor;

IF IsValid(ids_data) THEN
DESTROY ids_data
END IF
end event




hzhxxx(程序方程) 于 2004-9-1 10:39:30

$PBExportHeader$dw_excel_columns.srd
$PBExportComments$临时得 转换对象
release 7;
datawindow(units=0 timer_interval=0 color=16777215 processing=1 HTMLDW=no print.documentname="" print.orientation = 0 print.margin.left = 110 print.margin.right = 110 print.margin.top = 96 print.margin.bottom = 96 print.paper.source = 0 print.paper.size = 0 print.prompt=no print.buttons=no print.preview.buttons=no grid.lines=0 )
header(height=68 color="536870912" )
summary(height=0 color="536870912" )
footer(height=0 color="536870912" )
detail(height=76 color="536870912" )
table(column=(type=char(40) updatewhereclause=no name=coltitle dbname="coltitle" )
column=(type=char(30) updatewhereclause=no name=colname dbname="colname" )
column=(type=long updatewhereclause=no name=x dbname="x" )
column=(type=char(10) updatewhereclause=no name=objtype dbname="objtype" )
column=(type=char(20) updatewhereclause=no name=coltype dbname="coltype" )
)
text(band=header alignment="2" text="Coltype" border="2" color="0" x="718" y="4" height="60" width="361" name=coltype_t font.face="宋体" font.height="-10" font.weight="400" font.family="0" font.pitch="2" font.charset="134" background.mode="2" background.color="80269524" )
text(band=header alignment="0" text="coltitle" border="2" color="0" x="1088" y="4" height="60" width="434" name=t_1 font.face="宋体" font.height="-10" font.weight="400" font.family="0" font.pitch="2" font.charset="134" background.mode="2" background.color="80269524" )
text(band=header alignment="0" text="objtype" border="2" color="0" x="1531" y="4" height="60" width="320" name=t_2 font.face="宋体" font.height="-10" font.weight="400" font.family="0" font.pitch="2" font.charset="134" background.mode="2" background.color="80269524" )
text(band=header alignment="2" text="Colname" border="2" color="0" x="9" y="4" height="60" width="457" name=colname_t font.face="宋体" font.height="-10" font.weight="400" font.family="0" font.pitch="2" font.charset="134" background.mode="2" background.color="80269524" )
text(band=header alignment="2" text="X" border="2" color="0" x="475" y="4" height="60" width="233" name=x_t font.face="宋体" font.height="-10" font.weight="400" font.family="0" font.pitch="2" font.charset="134" background.mode="2" background.color="80269524" )
column(band=detail id=1 alignment="0" tabsequence=32766 border="2" color="0" x="1088" y="0" height="72" width="434" format="[general]" name=coltitle edit.limit=0 edit.case=any edit.autoselect=yes font.face="宋体" font.height="-10" font.weight="400" font.family="2" font.pitch="2" font.charset="134" background.mode="2" background.color="16777215" )
column(band=detail id=4 alignment="0" tabsequence=32766 border="2" color="0" x="1531" y="0" height="72" width="320" format="[general]" name=objtype edit.limit=0 edit.case=any edit.autoselect=yes font.face="宋体" font.height="-10" font.weight="400" font.family="2" font.pitch="2" font.charset="134" background.mode="2" background.color="16777215" )
column(band=detail id=2 alignment="0" tabsequence=10 border="2" color="0" x="9" y="0" height="72" width="457" format="[general]" name=colname edit.limit=0 edit.case=any edit.focusrectangle=no edit.autoselect=yes edit.autohscroll=yes font.face="宋体" font.height="-10" font.weight="400" font.family="2" font.pitch="2" font.charset="134" background.mode="1" background.color="536870912" )
column(band=detail id=3 alignment="1" tabsequence=20 border="2" color="0" x="475" y="0" height="72" width="233" format="[general]" name=x edit.limit=0 edit.case=any edit.focusrectangle=no edit.autoselect=yes edit.autohscroll=yes font.face="宋体" font.height="-10" font.weight="400" font.family="2" font.pitch="2" font.charset="134" background.mode="1" background.color="536870912" )
column(band=detail id=5 alignment="0" tabsequence=30 border="2" color="0" x="718" y="0" height="72" width="361" format="[general]" name=coltype edit.limit=0 edit.case=any edit.focusrectangle=no edit.autoselect=yes edit.autohscroll=yes font.face="宋体" font.height="-10" font.weight="400" font.family="2" font.pitch="2" font.charset="134" background.mode="1" background.color="536870912" )
htmltable(border="1" )
htmlgen(clientevents="1" clientvalidation="1" clientcomputedfields="1" clientformatting="0" clientscriptable="0" generatejavascript="1" )

上面的程序 Bug 列表 :
1.

/**********************************************************/
//Function : 转换数据到 excel
//parm :
// 1. as_title : excel 的标题
//return : 1 is success and -1 is fail
//Author : hzh
//date : 2003.12.08
//Modifier :
// 1. 2003.12.10 by hzh
//Reason :
// 1. 增加对计算列的处理
/**********************************************************/

long l_cnt,l_i,l_cols,l_rows

string s_colnum ,s_colname,s_range

OLEObject xlapp , xlsub

FOR l_i = 1 TO UpperBound(is_columntitle)
IF IsNull(is_columntitle[l_i]) THEN EXIT
l_cols++
NEXT


2.
函数 : uf_initcolumn 处理 datetime 格式不是很好

CASE 'date'//,'datetime'
s_datatype = Lower(ds_excel.GetItemString(i_cnt,'coltype'))
IF s_datatype = 'datetime' THEN
is_columnformat[i_cnt] = 'yyyy-m-d h:mm'
ELSE
is_columnformat[i_cnt] = 'yyyy""年""m""月""d""日""'
END IF

3. 这个不是错误,可以加强一下功能
//特别指定日期专用格式为 char(10)
s_datatype = Lower(ds_excel.GetItemString(i_cnt,'coltype'))
IF s_datatype = 'char(10)' THEN
is_columnformat[i_cnt] = 'yyyy""年""m""月""d""日""'
END IF

//特别指定时间专用格式为 char(8)
s_datatype = Lower(ds_excel.GetItemString(i_cnt,'coltype'))
IF s_datatype = 'char(8)' THEN
is_columnformat[i_cnt] = 'h""时""mm""分""ss""秒""'
END IF

//特别指定日期时间专用格式为 char(19)
s_datatype = Lower(ds_excel.GetItemString(i_cnt,'coltype'))
IF s_datatype = 'char(19)' THEN
is_columnformat[i_cnt] = 'yyyy-m-d h:mm'
END IF

根据代码,只有 char(8),10,19 才有啊,这是我设计日期,时间等的专用格式



balloonman2002(Blog.csdn.net/balloonman2002 - 抵制日货) 于 2004-9-1 10:55:55

我再把另外一个帖子当中中国龙的方法也贴过来,那个帖子可能由于CSDN历史帖子管理原因无法成功添加为FAQ,也很可惜,大家如果有其他好的方法也请一并贴上来:

llitcwl(中国龙):

//====================================================================
// [PUBLIC] Function uf_data2excel 在 u_data2word inherited from nonvisualobject
//--------------------------------------------------------------------
// 说明:将数据倒入excel中,支持计算列及显示格式,要求在题头的计算列要写tag值
//--------------------------------------------------------------------
//参数1:[value] datawindow adw
//说明:数据窗口
//--------------------------------------------------------------------
// 返回:(INTEGER) 成功返回1,不成功返回0
//--------------------------------------------------------------------
// 作者:cwl日期: 2002.03.18
//====================================================================
//变更日志:020515加入对交叉表倒出的支持(主要是修改了保存题头部分)

constant integer ppLayoutBlank = 12
OLEObject ole_object
ole_object = CREATE OLEObject

integer li_ret,li_crosstab=0
long ll_colnum,ll_rownum
string ls_value
string ls_objects,ls_obj,ls_objs[],ls_objtag[]
long ll_pos,ll_len,ll_num = 0
//题头区
long ll_headnum
string ls_head[],ls_headtag[]
//合计区
long ll_sumnum,i=1,startpos=1,endpos,li_pos
string ls_sum[],ls_sumtag[],ls_bind,token[],list,ls_temp,ls_crosstabcol
n_cst_string lu_string //PFC string处理对象

li_ret = ole_object.ConnectToObject("","Excel.Application")
IF li_ret <> 0 THEN
//如果Excel还没有打开,则新建。
li_ret = ole_object.ConnectToNewObject("Excel.Application")
if li_ret <> 0 then
MessageBox('OLE错误','OLE无法连接!错误号:' + string(li_ret))
return 0
end if
ole_object.Visible = false//不可见
END IF

if adw.Object.DataWindow.Processing='4' then //交叉表处理
adw.Object.DataWindow.Crosstab.StaticMode='true'//将数据静态化
li_crosstab=1
end if

pointer oldpointer
oldpointer = SetPointer(HourGlass!)

//新增一个工作区
ole_object.Workbooks.Add



ls_objects = trim(adw.Describe('datawindow.Objects'))
list=ls_objects
EndPos= pos(list, '~t', StartPos)
//得到对象列表
Do while ( EndPos > 0 )
token[i] = Mid(list, StartPos, EndPos - StartPos)
i ++
StartPos = EndPos + 1
EndPos= pos(list, '~t', StartPos)
LOOP
token[i] = Mid(list, StartPos)
ll_rownum=UpperBound(token)

for i=1 to ll_rownum
ls_obj = token[i]
if ls_obj='title' then messagebox('',adw.Describe(ls_obj + '.type'))
if lower(adw.Describe(ls_obj + '.type')) = 'column' or &
lower(adw.Describe(ls_obj + '.type')) = 'compute' then
ls_bind=lower(adw.Describe(ls_obj + '.band'))
if ls_bind = 'detail' then
ll_num += 1
ls_objs[ll_num] = ls_obj
if li_crosstab=0 then //一般处理
ls_objtag[ll_num] = adw.Describe(ls_obj + '_t.text')
elseif li_crosstab=1 then //交叉表处理
li_pos=lu_string.of_lastpos(ls_obj,'_',len(ls_obj))//找出最后一次出现'_'的位置
if li_pos=0 or (not isnumber(mid(ls_obj,li_pos+1))) then //不是交叉列
ls_objtag[ll_num] = adw.Describe(ls_obj + '_t.text')
else
ls_temp=mid(ls_obj,li_pos)
ls_crosstabcol=mid(ls_obj,1,li_pos - 1)//取出交叉列名
//messagebox('',ls_crosstabcol+',,,,'+ls_temp)
ls_objtag[ll_num]=adw.Describe( ls_crosstabcol + "_t"+ls_temp+".Text" )//取出交叉表的题头
end if
end if
elseif (ls_bind = 'summary') then
ll_sumnum += 1
ls_sum[ll_sumnum] = ls_obj
ls_sumtag[ll_sumnum] = adw.Describe(ls_obj + '.tag')
else
ll_headnum += 1
ls_head[ll_headnum] = ls_obj
ls_headtag[ll_headnum] = adw.Describe(ls_obj + '.tag')
end if

end if

next

//得到数据窗口数据的列数与行数(行数应该是数据行数 + 2)
ll_colnum = ll_num
ll_rownum = adw.rowcount() + 2

string column_name
string ls_colname
integer j,k
//写题头
for i=1 to ll_headnum
ls_value = ls_headtag[i]
if ls_value<>'?' then
ole_object.cells(1,(i - 1)*2+1).value = ls_value
end if
column_name = ls_head[i]
ls_value=this.uf_getdata(adw,column_name,1)
ole_object.cells(1,(i)*2).value = ls_value
next
//写结尾
for i=1 to ll_sumnum
ls_value = ls_sumtag[i]
if ls_value<>'?' then
ole_object.cells(ll_rownum+1,(i - 1)*2+1).value = ls_value
end if
column_name = ls_sum[i]
ls_value=this.uf_getdata(adw,column_name,1)
ole_object.cells(ll_rownum+1,(i)*2).value = ls_value
next

//写标题
for i = 1 to ll_colnum
//得到标题头的名字
ls_value = ls_objtag[i]
ole_object.cells(2,i).value = ls_value
next
//写数据
for i = 3 to ll_rownum
for j = 1 to ll_colnum
column_name = ls_objs[j]
ls_value=this.uf_getdata(adw,column_name,i - 2)
ole_object.cells(i,j).value = ls_value
next
next

SetPointer(oldpointer)
ole_object.Visible = True
ole_object.disconnectobject()
DESTROY ole_object

return 1



//====================================================================
// [PUBLIC] Function uf_getdata 在 u_data2word inherited from nonvisualobject
//--------------------------------------------------------------------
// 说明:得到一个数据窗口列及计算列的准确显示值
//--------------------------------------------------------------------
//参数1:[value] datawindow dw_1
//说明:
//参数2:[value] string col
//说明:对象名
//参数3:[value] integer row
//说明:行
//--------------------------------------------------------------------
// 返回:(STRING) 值
//--------------------------------------------------------------------
// 作者:cwl日期: 2002.03.18
//====================================================================
string ls_edittype,ls_value,ls_format
integer id
ls_edittype=lower(dw_1.Describe(col+".Edit.Style"))//得到编缉风格
choose case ls_edittype
case 'ddlb','dddw'//应该得到显示值
ls_value=dw_1.describe( "Evaluate('LookUpDisplay("+col+") ',"+string(row)+" )")
case else
id=long(dw_1.Describe(col+".id"))
ls_format=dw_1.Describe(col+".Format")
if mid(ls_format,1,1)='[' or ls_format='?' or ls_format='' then //不作格式处理
if id=0 then //计算列
ls_value=dw_1.Describe("Evaluate(~"" + dw_1.Describe(col + '.expression')&
+ "~","+string(row)+")")
else
ls_value=string(dw_1.object.data[row,id])
end if
else
if id=0 then //计算列
ls_value=string(dw_1.Describe("Evaluate('" + dw_1.Describe(col + '.expression')&
+ "',"+string(row)+")"),ls_format)
else
ls_value=string(dw_1.object.data[row,id],ls_format)
end if
end if
end choose
if isnull(ls_value) then ls_value=''
return ls_value


或者直接存成html文件

----------------------------------------------------------




th820901(四水)(月光如水水如天) 于 2004-9-1 11:03:18

偶UP,偶收藏!!



th820901(四水)(月光如水水如天) 于 2004-9-1 11:06:15

我記得以前陈偉也整理過,可惜找不到了 :)



workhand(我可憨了...) 于 2004-9-1 11:35:00

继续响应,这是以前一位仁兄的代码:


/**********************************************************/
/*函数名称:uf_dwsaveas_excel
功能:将数据窗口数据导出EXCEL文件,并将EXCEL文件默认英文标题替换成中文。
参数:datawindow datawin,为用户要导出数据窗口的数据窗口控件名
返回值:integer 1,success;-1,error
流程描述:先用saveasAscii()倒出为excel文件,再替换表头为中文名
设计人:yanhui2003年11月
修改人:叶文林 2004.4.8
原因:为提高程序的可读性作了少量的修改(如:增加注释、改变排版风格等)*/
/**********************************************************/

/***************以下程序将导出为EXCEL文档******************/
integer li_rtn,ii,li_asc
string ls_name,ls_pathname
boolean lb_exist
if datawin.RowCount()<1 then
MessageBox("提示信息","请先检索数据再导出至Excel!")
return -1//error
end if
li_rtn=GetFileSaveName("保存文件",ls_pathname,ls_name,"xls","Excel文件(*.xls),*.xls")

if li_rtn=1 then
lb_exist = FileExists(ls_pathname)
IF lb_exist THEN
li_rtn = MessageBox("保存", ls_pathname+"已经存在,是否覆盖?",Exclamation!, YesNo!)
end if
if li_rtn=1 then
//当文件存在用户选择覆盖,或是文件本就不存在时。注意变量li_rtn
li_rtn=datawin.SaveAsAscii(ls_pathname)
if li_rtn=1 then
//MessageBox("提示信息","导出数据成功!")
else
MessageBox("错误信息","导出数据失败!")
return -1//error
end if
else
return -1//error
end if
else
return -1
end if

/**********以下程序将导出的EXCEL英文标题替换为汉字*********/
long numcols , numrows , c, r
OLEObject xlapp , xlsub
int ret
numcols = long(datawin.Object.DataWindow.Column.Count)
numrows = datawin.RowCount()

// 产生oleobject的实例
xlApp = Create OLEObject

//连接ole对象
ret = xlApp.ConnectToNewObject( "Excel.Sheet" )
if ret < 0 then
MessageBox("连接失败!","连接到EXCEL失败,请确认您的系统是否已经安装EXCEL!~r~n"&
+"错误代码:"+string(ret))
return -1
end if
// 打开EXCEL文件
xlApp.Application.Workbooks.Open(ls_pathname)
////使文件可见
//xlApp.Application.Visible = true

// 得到活动工作表的引用,改善程序性能
xlsub = xlapp.Application.ActiveWorkbook.Worksheets[1]
string ls_colname,ls_text,ls_modistr,ls_col
//取字段名更改为对应的文本text值
FOR c=1 to numcols
ls_col="#"+string(c)+".name"
ls_colname=datawin.describe(ls_col)
ls_modistr=ls_colname+"_t.text"
ls_text=datawin.describe(ls_modistr)
xlsub.cells[1,c]=ls_text
NEXT

xlApp.DisConnectObject()
Destroy xlapp
MessageBox("提示信息","导出数据成功!")
return 1//success