teratail header banner
teratail header banner
質問するログイン新規登録
Win32 API

Win32 APIはMicrosoft Windowsの32bitプロセッサのOSで動作するAPIです。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

Q&A

解決済

3回答

4485閲覧

win32comライブラリーを使ったエクセル操作時の最終行取得方法と列挿入方法を教えてください。

yujin1202

総合スコア61

Win32 API

Win32 APIはMicrosoft Windowsの32bitプロセッサのOSで動作するAPIです。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

0グッド

0クリップ

投稿2021/04/07 07:40

編集2021/04/07 10:17

0

0

win32comライブラリをPythonを使い、エクセル操作しております。
VBAで言うところの最終行取得(Rows.Count)に関しての質問です。
よろしくお願いいたします。

下記の様なコードを書いております。

<test.py>

1 import win32com.client 2 from win32com.client import Dispatch 3 import os 4 path1=os.getcwd() 5 path2="./myExcel_old.xlsx" 6 path3="./myExcel_new.xlsx" 7 xl=win32com.client.Dispatch("Excel.Application") 8 xl.Visible=False 9 path=os.path.join(path1,path2) 10 pathx=os.path.join(path1,path3) 11 wb = xl.Workbooks.Open(path) 12 ws=wb.Worksheets["Sheet2"] 13 ws=activate 14 max_Rows=ws.Rows.Count 15 for i in range (2,max_Rows): 16   xl.Cells(i,2).Value=xl.WorksheetFunction.CountIf(xl.Range(ws.Cells(2,1),ws3.Cells(i,1)),ws.Cells(i,1).Value) 17 ws.Columns(1).Insert 18 wb.SaveAs(pathx) 19 wb.Close(SaveChanges=True)

Q1) 
14行目から16行目で、最終行を取得して、CountIFで処理を行い、別ファイル名にて保存すると言うコードになります。
しかし、上記のコードを実行すると、下記のエラーが発生します。
このエラーの意味は何になるのでしょうか? また、解決方法を教えて頂きたく。

========================

C:\Users\test_users\Desktop>python test8z3.py Traceback (most recent call last): File "test8z3.py", line 35, in <module> xl.Cells(i,2).Value=xl.WorksheetFunction.CountIf(xl.Range(ws3.Cells(2,1),ws3.Cells(i,1)),ws3.Cells(i,1).Value) File "<COMObject <unknown>>", line 2, in CountIf pywintypes.com_error: (-2147352567, '例外が発生しました。', (0, 'Microsoft Excel', '引数の数の誤りがあります。', 'xlmain11.chm', 0, -2146827284), None)

============================

不思議なのは、14行目をコメントアウトして、15行目のmax_Rowsを数値(例えば、300)に置き換えると(つまり、下記の様にすると)、

14 # max_Rows=ws.Rows.Count 15 for i in range (2,300): 16 xl.Cells(i,2).Value=xl.WorksheetFunction.CountIf(xl.Range(ws.Cells(2,1),ws3.Cells(i,1)),ws.Cells(i,1).Value)

ちゃんとCountifが正常に動き、別名でファイル保存もできます。(上記例では、300行まで動きます。エラーも発生しません。)

Q2)
なお、追加質問で恐縮なのですが、17行名の列追加のコードが機能しません。
エラーは出ないのですが、出来上がってきたファイルに、列が追加されておりません。(A列を追加するコードなのですが。)
こちらも、なぜ動作しないのかが分からず、困っております。

教えて頂きたく。
よろしくお願いいたします。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

y_waiwai

2021/04/07 08:12

このままではコードが読めないので、質問を編集し、<code>ボタンを押し、出てくる’’’の枠の中にコードを貼り付けてください
yujin1202

2021/04/07 10:18

<code>ボタンと言うのがあったのですね。 知りませんでした。 大変、失礼しました。 はい。 編集致しました。よろしくお願いいたします。
guest

回答3

0

14行目~17行目ですが、コメントに従い、下記の様に修正した所、Q1)とQ2)が共に解決しました。

14 t_Rows=ws.UsedRange.Row + ws.UsedRange.Rows.Count 15 for i in range (2,t_Rows): 16 xl.Cells(i,2).Value=xl.WorksheetFunction.CountIf(xl.Range(ws3.Cells(2,1), ws3.Cells(i,1)),ws3.Cells(i,1).Value) 17 ws3.Columns(1).Insert()

ありがとうございました。

投稿2021/04/07 15:23

yujin1202

総合スコア61

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

ベストアンサー

Q2)
なお、追加質問で恐縮なのですが、17行名の列追加のコードが機能しません。
エラーは出ないのですが、出来上がってきたファイルに、列が追加されておりません。(A列を追加するコードなのですが。)
こちらも、なぜ動作しないのかが分からず、困っております。

Insertはメソッドなので、

Python

1ws.Columns(1).Insert()

ではないかと。


以下追記します。

簡単なプログラムですが、以下で列が追加されたことを確認できました。

Python

1import win32com.client as com 2 3# エクセルを起動する 4excel = com.Dispatch("Excel.Application") 5 6# ワークブックを開く 7book = excel.Workbooks.Open("Book1.xlsx") 8 9# 開いたブックのシートをアクティブにする 10sheet = book.Worksheets("Sheet1") 11 12# A列に追加する 13sheet.Columns(1).Insert() 14# あるいは 15# sheet.Columns('A').Insert() 16# あるいは 17# sheet.Columns.Item(1).Insert() 18# あるいは 19# cols = sheet.Columns(1) 20# cols.Insert() 21# cols = None 22# いずれでも成功しました 23sheet = None 24 25# ワークブックを別名で保存 26book.SaveAs('Book1a.xlsx') 27 28# ブックを閉じる 29book.Close() 30book = None 31 32# エクセルを終了する。 33excel.Quit() 34excel = None

当方の環境は
Windows 10 Home (64bit)
Python 3.8.8 (64bit)
pywin32 300 (win32com)

投稿2021/04/07 09:56

編集2021/04/07 13:39
Bull

総合スコア986

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

yujin1202

2021/04/07 12:08

早速の御回答をありがとうございます。 私も最初、ご指摘の通りだと思って、そうしていたのですが、全く同じ現象でした。 (つまり、エラーは出ないのですが、出来上がってきたファイルに、列が追加されておりません。) 念のため、今、再度やってみたのですが、同じでした。 よろしくお願いいたします。
Bull

2021/04/07 13:40

プログラムを追記しました。
yujin1202

2021/04/07 15:18

ありがとうございます。 Q1)の最終行の部分を修正した上で、17行目を御指摘頂いた下記に書き直したところ、確かに列追加ができました。 *** ws.Columns(1).Insert() *** 逆に、14行目~16行目の部分で、最終行取得が間違っていると、上のコードがちゃんと動かない事も確認しました。(なぜだろうか???) いつも御支援をありがとうございます。 本件、解決致しました。深謝です。
guest

0

ws.Rows.Count ≠ データのある最終行
なので、そこを
ws.UsedRange.Row + ws.UsedRange.Rows.Count - 1
にすればOKでしょう。

「データのある最終行」については、こちら様サイトに詳しいです。

【落とし穴に注意】VBAで最終行の行番号を取得する
https://www.excelspeedup.com/vbalastrow/

投稿2021/04/07 09:38

FromMZ1500

総合スコア496

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

yujin1202

2021/04/07 15:10

ありがとうございます。 max_Rows=ws.UsedRange.Row + ws.UsedRange.Rows.Count - 1 とする事で、確かに最終行を取得できました。 ありがとうございました。 リンクもよく読んでみます。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.30%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問