找回密码
 加入
搜索
查看: 12602|回复: 16

[AU3基础] 打开Excel,并读取表格出错,何因?[已解决]

  [复制链接]
发表于 2012-11-13 12:25:14 | 显示全部楼层 |阅读模式
本帖最后由 blue_dvd 于 2012-11-23 23:18 编辑

打开一个Excel,并读取表格出错,何因?
#include <File.au3>
#include <Excel.au3>
#include <Array.au3>
#include <GuiListView.au3>
#include <ListViewConstants.au3>
#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>

;打开一个选文件对话框;
Local $sFilePath1=FileOpenDialog("选择导入电子表格文件", @ScriptDir&"", "Microsoft Excel 工作薄 (*.xls)", 1+2+4)

Local $oExcel = ObjGet($sFilePath1, "Excel.Application") 

If @error Then
    MsgBox(0, "警告", "Error Getting an active Excel Object. Error code: " & Hex(@error, 8))
    Exit
EndIf

;读取Excel表格到数组

Local $aArray =_ExcelReadSheetToArray($oExcel)

If @error Then
    MsgBox(0, "警告", "Error Getting an active Excel Object. Error code: " & Hex(@error, 8))
    Exit
EndIf

_ArrayDisplay($aArray, "使用默认参数")  ;检测数组是否正确。
 
错误如下:
H:\autoit3\Include\Excel.au3 (787) : ==> ???????????("Object").:
Local $sLastCell = $oExcel.Application.Selection.SpecialCells($xlCellTypeLastCell).Address(True, True, $xlR1C1)
Local $sLastCell = $oExcel.Application.Selection^ ERROR
->12:23:56 AutoIT3.exe 完成:[CODE]:1
+>12:23:57 ACNWrapper 完成..
>退出代码: 1        运行时间: 10.908 秒

解决方法在11楼!
发表于 2012-11-13 19:39:21 | 显示全部楼层
可能你的表格打开后选中的是个图形或者其他什么,而不是单元格,UDF中用的是selection,这个是excel当前选中项,而只有选中单元格区域的时候,后面的specialcells才有效,你可以自己打开excel文件检查一下是不是这个原因
 楼主| 发表于 2012-11-13 20:56:45 | 显示全部楼层
回复 2# kevinch
Local $oExcel = ObjGet($sFilePath1, "Excel.Application") 
换成
$oExcel = _ExcelBookOpen($sFilePath1)
就能运行了,但是却打开了Excel,能否不打开excel,直接ListView显示呢?
 楼主| 发表于 2012-11-13 20:59:34 | 显示全部楼层
头都爆了,不知道何因?
发表于 2012-11-13 21:38:38 | 显示全部楼层
Local $oExcel = ObjGet($sFilePath1) 
objget不用后面的参数试下
 楼主| 发表于 2012-11-14 17:59:38 | 显示全部楼层
回复 5# kevinch
不用后面的参数
Local $oExcel = ObjGet($sFilePath1)
还是有错
H:\autoit3\Include\Excel.au3 (787) : ==> ???????????("Object").:
Local $sLastCell = $oExcel.Application.Selection.SpecialCells($xlCellTypeLastCell).Address(True, True, $xlR1C1)
Local $sLastCell = $oExcel.Application.Selection^ ERROR
->17:57:17 AutoIT3.exe 完成:[CODE]:1
+>17:57:19 ACNWrapper 完成..
>退出代码: 1        运行时间: 11.893 秒
发表于 2012-11-14 19:09:21 | 显示全部楼层
同一个问题出的错,不如楼主把excel文件共享一下看看啦
 楼主| 发表于 2012-11-14 21:18:20 | 显示全部楼层
回复 7# kevinch

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?加入

×
 楼主| 发表于 2012-11-14 21:20:36 | 显示全部楼层
请kevinch老师帮忙看看怎么回事?打开总出错!
发表于 2012-11-14 21:49:44 | 显示全部楼层
本帖最后由 kevinch 于 2012-11-14 22:02 编辑

Local $aArray =_ExcelReadSheetToArray($oExcel)
换成
Local $aArray=$oExcel.activesheet.usedrange.value
就可以了,是因为UDF中的判断方式不太好造成的错误,应该算是个bug吧,其实可以这样直接读取已使用区域的值来获取一个二维数组,但是相对于excel的工作表来讲,得到的行列是反的,这点需要注意

或者用下面这样的方法转置一下
Local $aArray=$oExcel.application.transpose($oExcel.activesheet.usedrange.value)
发表于 2012-11-14 22:00:15 | 显示全部楼层
本帖最后由 kevinch 于 2012-11-15 08:39 编辑
Func _ExcelReadSheetToArray($oExcel, $iStartRow = 1, $iStartColumn = 1, $iRowCnt = 0, $iColCnt = 0, $iColShift = True)
        Local $avRET[1][1]
        
        If Not IsObj($oExcel) Then Return SetError(1, 0, 0)
        If $iStartRow < 1 Then Return SetError(2, 0, 0)
        If $iStartColumn < 1 Then Return SetError(2, 1, 0)
        If $iRowCnt < 0 Then Return SetError(3, 0, 0)
        If $iColCnt < 0 Then Return SetError(3, 1, 0)

        With $oExcel
                $lastcell=.activesheet.cells.SpecialCells($xlCellTypeLastCell)

                If $iStartRow>$lastcell.row Then Return SetError(2, 0, 0)
                If $iStartColumn>$lastcell.column Then Return SetError(2, 1, 0)
                If $iStartRow + $iRowCnt-1 > $lastcell.row Then Return SetError(3, 0, 0)
                If $iStartColumn + $iColCnt-1 > $lastcell.column Then Return SetError(3, 1, 0)
                
                If $iRowCnt=0 Then $iRowCnt=$lastcell.row-$iStartRow+1
                If $iColCnt=0 Then $iColCnt=$lastcell.column-$iStartColumn+1
                
                If .activesheet.cells($iStartRow,$iStartColumn).resize($iRowCnt,$iColCnt).cells.count=1 Then
                        $avRET[0][0]=.activesheet.cells($iStartRow,$iStartColumn).value
                Else
                        $avRET=.activesheet.cells($iStartRow,$iStartColumn).resize($iRowCnt,$iColCnt).value
                        If $iColShift Then $avRET=$oExcel.application.transpose($avRET)
                EndIf
        EndWith
        Return $avRET
EndFunc
改一下那个UDF函数
 楼主| 发表于 2012-11-15 12:26:45 | 显示全部楼层
回复 11# kevinch
还是报错!是不是用法要改?
Local $aArray =_ExcelReadSheetToArray($oExcel)
我修改了UDF函数为
Func _ExcelReadSheetToArray($oExcel, $iStartRow = 1, $iStartColumn = 1, $iRowCnt = 0, $iColCnt = 0, $iColShift = True)
        Local $avRET[1][1]
        
        If Not IsObj($oExcel) Then Return SetError(1, 0, 0)
        If $iStartRow < 1 Then Return SetError(2, 0, 0)
        If $iStartColumn < 1 Then Return SetError(2, 1, 0)
        If $iRowCnt < 0 Then Return SetError(3, 0, 0)
        If $iColCnt < 0 Then Return SetError(3, 1, 0)

        With $oExcel
                $lastcell=.activesheet.cells.SpecialCells($xlCellTypeLastCell)

                If $iStartRow>$lastcell.row Then Return SetError(2, 0, 0)
                If $iStartColumn>$lastcell.column Then Return SetError(2, 1, 0)
                If $iStartRow + $iRowCnt-1 > $lastcell.row Then Return SetError(3, 0, 0)
                If $iStartColumn + $iColCnt-1 > $lastcell.column Then Return SetError(3, 1, 0)
                
                If $iRowCnt=0 Then $iRowCnt=$lastcell.row-$iStartRow+1
                If $iColCnt=0 Then $iColCnt=$lastcell.column-$iStartColumn+1
                
                If .activesheet.cells($iStartRow,$iStartColumn).resize($iRowCnt,$iColCnt).cells.count=1 Then
                        $avRET[0][0]=.activesheet.cells($iStartRow,$iStartColumn).value
                Else
                        $avRET=.activesheet.cells($iStartRow,$iStartColumn).resize($iRowCnt,$iColCnt).value
                        If $iColShift Then $avRET=$oExcel.application.transpose($avRET)
                EndIf
        EndWith
        Return $avRET
EndFunc
发表于 2012-11-15 19:07:40 | 显示全部楼层
那就奇怪了,我这里已经正常了的
发表于 2012-11-15 20:43:53 | 显示全部楼层
学习一下也,
 楼主| 发表于 2012-11-16 22:22:32 | 显示全部楼层
回复 13# kevinch
确实是可以了,多谢了!但是原来在数组$aArray[0][0]和$aArray[0][1]处放有行数和列数,用了你改的函数后就没有了,能恢复吗?
您需要登录后才可以回帖 登录 | 加入

本版积分规则

QQ|手机版|小黑屋|AUTOIT CN ( 鲁ICP备19019924号-1 )谷歌 百度

GMT+8, 2024-9-28 04:21 , Processed in 0.088182 second(s), 24 queries .

Powered by Discuz! X3.5 Licensed

© 2001-2024 Discuz! Team.

快速回复 返回顶部 返回列表