あなたの習慣について教えてください!!

既に該当のファイルが開いているのなら閉じたいのですが
xlBook.Quitだとエラーになります。

Sub test1()
Dim xlApp As Excel.Application
Dim xlBook As Workbook
Dim FileName As String

FileName = "C:\test.xlsm"

Set xlApp = GetObject("", "Excel.Application") 'GetObjectで合ってるか不安
Set xlBook = xlApp.Workbooks.Open(FileName)

If xlBook.ReadOnly = True Then 'ファイルが開いてるのなら
MsgBox "既にファイルが開いているので閉じます。"
xlBook.Quit 'エラー 438
End If

xlApp.Quit 'これって何のために必要?

Set xlBook = Nothing 'ココを通り過ぎるのにすごく時間がかかる。
Set xlApp = Nothing
End Sub

と言うコードを作りました。
xlBook.Quitがダメならどのコードを使えばいいでしょう?

また、
GetObject("", "Excel.Application")
と言う開き方でいいのでしょうか?

あと、
xlApp.Quit
は何のために必要なのでしょう?

タスクマネージーのプロセスを見ると、
Set xlApp = GetObject("", "Excel.Application")
を通る時に新しいEXCEL.EXEが作成され、
Set xlApp = Nothing
を通り過ぎる時に、そのEXCEL.EXEが消えます。

だから
xlApp.Quit
は不要ですか?

A 回答 (4件)

少し考えて、こんな風に


既存のExcelが立ち上がっていた場合でも
下の処理中にトラブルがあっても巻き添えにしないために
新たなインスタンスを作成して、その中で処理した方が安全と考えます。
InUse関数はネットワーク上で他人が開いていた場合にも有効です。

Sub test1a()
Dim xlApp As Excel.Application
Dim xlBook As Excel.Workbook
Dim FileName As String

FileName = "C:\test.xlsm"

'開いているかチェック
If InUse(FileName) <> 0 Then
MsgBox "ファイルが見つからないか、既に開かれています"
Exit Sub
End If

Set xlApp = GetObject("", "Excel.Application") '新規にExcelのインスタンスを作成
'Set xlApp = CreateObject("Excel.Application") ’こちらでも可
Set xlBook = xlApp.Workbooks.Open(FileName)

If xlBook.ReadOnly Then '読み取り専用
MsgBox "既にファイルが開いているので閉じます。"
GoTo CloseP
End If

If xlBook.MultiUserEditing Then '共有モードも閉じて良い?
MsgBox "共有モードで開かれていますので閉じます。"
GoTo CloseP
End If

xlApp.Visible = True '必要に応じて
'ここいら辺から本番の処理

CloseP: '終了処理
xlBook.Close SaveChanges:=True 'で良かったのかな?
Set xlBook = Nothing '解放
xlApp.Quit 'Excel の終了
Set xlApp = Nothing
End Sub

Function InUse(ByVal FileName As String) As Integer
'メモ帳などのような'ファイルをロックしないアプリが開いていた場合は機能せず。
'Excelファイルが共有モードで開かれていた場合も、0 が返ります。
'FileName にはフルパスで渡すこと
Dim fNo As Integer
fNo = FreeFile
On Error Resume Next
Open FileName For Input Access Read Lock Read Write As fNo

Select Case err.Number
Case 0 '開かれていない
InUse = 0
Case 53 'ファイルが見つからない
InUse = 1
Case 70 '開かれている
InUse = 2
Case Else 'ここに来た経験は無いのですが念のため
InUse = 3
End Select

Close fNo

End Function
    • good
    • 0
この回答へのお礼

ありがとうございます。

お礼日時:2013/01/28 09:06

順不同に



> xlBook.Quit 'エラー 438
Quitは、アプリケーションから抜け出す時に使います。
なので、ブック(ファイル)に対しては有効ではありません。
・・と覚えれば目安になるかと思います。

> xlBook.Quitがダメならどのコードを使えばいいでしょう?
通例、xlBook.Close で、該当ブックの子ウィンドウを閉じます。



> GetObject("", "Excel.Application")
> と言う開き方でいいのでしょうか?
良いと思います。

ですが、ご自身でも確認された通り、
> Set xlApp = GetObject("", "Excel.Application")
> を通る時に新しいEXCEL.EXEが作成され、
ますから、この挙動で良ければ、と言う条件が付きます。

逸れますが、この「新しく立ち上がったエクセルアプリケーションを終了するために
> xlApp.Quit
> は何のために必要なのでしょう?
上述、xlBook.Close だけでは、アプリケーションが無駄に残ってしまいますから、
コレを閉じるために必要です。

新しくアプリケーションを立ち上げず、子ウィンドウを開くだけなら
  Set xlBook = Workbooks.Open(FileName)
でも可能です。
この場合、FileNameと言うブックを開くマクロを走らせたブックは残しておくので、
アプリケーション終了は必要ありません。
なので、.Quit は不要と言えます。



ところで、
> If xlBook.ReadOnly = True Then 'ファイルが開いてるのなら
と言う条件を付けていますが、これはどうでしょう?
ファイル自体に「読み取り専用」属性を設定していても反応してしまい、
この場合も閉じてしまいますね。
なので、

Dim OBook As Workbook
Dim FileName As String

FileName = "c:\test.xlsm"

  For Each OBook In Workbooks  '開いている全てのブックに関して
    If OBook.FullName = FileName Then   '名前が同じだったら
      MsgBox "既にファイルが開いているので中止します。"
      Exit Sub   'マクロ終了
    End If
  Next

  'Forを抜けてきたら=同名のファイルが開いていなかったら
  Workbooks.Open FileName   'ファイルを開く

こんなやり方を提案。
参考までにどうぞ。
    • good
    • 0
この回答へのお礼

ありがとうございます。

お礼日時:2013/01/28 09:06

これは、どのアプリ上で実行されているのでしょう?Excel?Access?・・


それによって話は変わってくるかと。

取りあえず
>Set xlApp = GetObject("", "Excel.Application")
>を通る時に新しいEXCEL.EXEが作成され、
は、
ヘルプに記載が有りますよ。
以下抜粋
GetObject([pathname] [, class])
引数 pathname に長さ 0 の文字列 ("") を指定すると、GetObject 関数は、指定した種類の新しいオブジェクト インスタンスを返します。
引数 pathname を省略すると、GetObject 関数は、指定した種類で現在アクティブになっているオブジェクトを返します。
    • good
    • 0
この回答へのお礼

エクセルで実行するのかアクセスで実行するかによって変わるのですか。
アクセスから実行するつもりです。

現在アクティブになっているオブジェクトを返したいか
新しいオブジェクト インスタンスを返したいかによって
pathnameの値を変えればいいのですね。

お礼日時:2013/01/25 21:09

xlBook.Close はファイルを閉じます。


xlApp.Quit はEXCELを終わらせます。
必要かどうかは使い方次第です。
    • good
    • 0
この回答へのお礼

xlBook.QuitではなくCloseを使うのですか。ありがとうございました。

お礼日時:2013/01/25 21:09

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!

このQ&Aを見た人はこんなQ&Aも見ています


おすすめ情報