转:如何复制多于 16,383 条记录到 Excel 中

    技术2022-05-11  129

    转:如何复制多于 16,383 条记录到 Excel 中

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

    qxf 于提供, CY 和 rmh 翻译 

    VFP 的 COPY TO TYPE XL5 命令只能复制 16,383 条记录. 该限制是由于 XL5 格式的一张工作表只能有 16,383 行的限制造成的 (参见 MSKB Q103355). 在 Excel 97 和 Excel 2000 中的最大行数是 65,536. 不幸的中在 VFP 中没有 TYPE XL8 关键字. 下面的代码提供一种简单的处理办法. 程序 Copy2Xls 可用于替代 VFP 自己的 COPY TO TYPE XL5 命令. 程序使用了 VFP 6 新增的 TYPE CSV 关键字. 如果你使用早期版本的 VFP, 用 FOX2X 替换 CSV 关键字. 关于 CSV 与 FOX2X 的区别及一些限制参见程序头中的注释. (以下程序用 UT 上的 Mike Hellands great utility mhHtmlCode 程序格式)

     *  程序...........: Copy2xls.prg *  作者............: Daniel Gramunt *  项目...........: common *  创建...........: 11.10.2000  17:25:06 *) 说明.......: 替换 VFP 自己的 COPY TO TYPE XL5 命令. *)                   : Excel 5 和 Excel 95 有一个限制就是一张工作表只能有 16,383 行. *)                   : 该限制在 Excel 97 和 Excel 2000 是 65,536 行. *)                   : 由于没有 TYPE XL8 命令, VFP 只能复制最初的 16,383 条记录. *)                   : *)                   : 该程序处理该限制并允许复制用户机器上的 Excel 版本所支持的记录数. *)                   : *)                   : 该方案是非常简单的: *)                   :  1. COPY TO TYPE CSV *)                   :  2. 打开 CSV 文件并用 Automation 来 SaveAs(tcExcelFile) *)                   : *)                   : 假定 MS Excel (Excel 97 或以上) 安装在用户的机器上 *)                   :  (好, 它将也可处理 Excel 5.0 和 95, 但将使用 16,383 的限制). *)                   : *)                   : 返回成功导出的记录数, 否则: *)                   :   -1 = 缺少参数或参数类型错误 *)                   :   -2 = 当前工作区中未打开表 *)                   :   -3 = 记录数超过最大 Excel 行数 *)                   :   -4 = 用户不想复盖已存在的 Excel 文件 (SET SAFETY = ON) *)                   : *)                   : 性能注意: 在 VFP 中的 COPY TO 命令比起任何 automation 都要快得多. *)                   :           但是, 由于我们只用来打开导出的文件并保存为不同格式, 几乎没有 *)                   :           性能损失. *)                   : *)                   : *  调用示例....: Copy2Xls("c:/temp/bidon.xls") *  参数列表....: tcExcelFile - 要创建的 Excel 文件的路径/文件名. *  主要修改....: 26.10.2000: COPY TO FOX2X 和 SaveAs() 代替 *                    :             "组合" 个别的 Excel 文件. *                    :             谢谢 UT 的 莈tin Bas鰖 的意见 *                    : 12.04.2000: COPY TO CSV 代替 FOX2X. *                    :             FOX2X 有以下限制: *                    :             - 代码页 850 的问题 (如字符 "?) *                    :             - 不支持长文件名 (虽然很容易处理) *                    :             - 不支持 datetime *                    :             CSV 没有上述问题, 但有其它限制: *                    :             - 逻辑字段转换为 F/T 而不是 FALSE/TRUE. *                    :               这不是一个问题, 但为了保持一致性, 我们 *                    :               对于记录数没有超过限制的表, *                    :               不再使用 VFP 自己的 COPY TO TYPE XL5. *                    :             - 如果一个字符字段只包括数值且值中包括前导的零, *                    :               Excel 转换它为数值型的值 (如 "00000100" => 100). *                    :               这是一个问题, 特别是字段是一个专用关键字且你又要在稍后从 *                    :               Excel 文件转换回 VFP 时. *-------------------------------------------------------------------------------------------------- LPARAMETER tcExcelFile  #INCLUDE FoxPro.h  #DEFINE xlWorkbookNormal      -4143     && 被 SaveAs() 用来保存于当前 Excel 版本 #DEFINE ccErrorNoParameter    "Parameter  : 参数丢失失或类型错误 (非 'C')" #DEFINE ccErrorNoTableOpen    "当前工作区中没有打开表" #DEFINE ccErrorToManyRows     "记录数" + ;                               ALLTRIM(TRANSFORM(lnRecords, "999,999,999")) +;                               ") 超过 Excel 最大行数 (" -;                               ALLTRIM(TRANSFORM(lnXlsMaxNumberOfRows, "999,999,999"))+;                               ")"  *-- 检查参数 IF VARTYPE(tcExcelFile) <> "C" OR EMPTY(tcExcelFile)     ??CHR(7)     WAIT WINDOW NOWAIT ccErrorNoParameter     RETURN -1 ELSE     tcExcelFile = ForceExt(tcExcelFile, "XLS") ENDIF  *-- 确信在选定的工作区中打开了表或游标 IF EMPTY(ALIAS())     ??CHR(7)     WAIT WINDOW NOWAIT ccErrorNoTableOpen     RETURN -2 ENDIF  LOCAL loXls, lnXlsMaxNumberOfRows, lnRecords, lnRetVal, lcTempDbfFile  loXls = CREATEOBJECT("excel.application") *-- 抑制 Excel 的警告和信息 (类似于 SET SAFETY OFF) loXls.DisplayAlerts = .f. *-- 从 Excel 获取最大行数. 在我们计算工作表中的行数前, 需要添加一个工作簿. loXls.workbooks.add() lnXlsMaxNumberOfRows = loXls.ActiveWorkBook.ActiveSheet.Rows.Count - 1 && 1 头行  lnRecords = RECCOUNT()  *-- 检查记录数是否超过了 Excel 的限制 IF lnRecords > lnXlsMaxNumberOfRows     ??CHR(7)     WAIT WINDOW NOWAIT ccErrorToManyRows     *-- 关闭 Excel     loXls.application.quit()     RETURN -3 ENDIF  *-- 维持 SET SAFETY IF SET("SAFETY") = "ON" AND FILE(tcExcelFile)     IF MESSAGEBOX(tcExcelFile + " 已经存在, 复盖它?",;                   MB_YESNO + MB_ICONQUESTION + MB_DEFBUTTON2) = IDNO         *-- 用户选择了  因此退出         *-- 关闭 Excel         loXls.application.quit()         RETURN -4     ENDIF ENDIF  lcTempDbfFile = AddBs(SYS(2023)) + SYS(3) + ".CSV"  COPY TO (lcTempDbfFile) TYPE CSV lnRetVal = _TALLY  *-- 打开导出的 CSV 文件 loXls.Application.Workbooks.Open(lcTempDbfFile)  *-- 保存为 Excel 文件 loXls.ActiveSheet.saveAs(tcExcelFile, xlWorkbookNormal)  *-- 删除 CSV 文件 IF FILE(lcTempDbfFile)     DELETE FILE (lcTempDbfFile) ENDIF  *-- 关闭 Excel loXls.application.quit()  RETURN lnRetVal


    最新回复(0)