2016-11-30 164 views
0

我寫在Excel中VBA的腳本與IfElseIf報表數據庫檢索。該搜索是通過UserForm具有兩個字段進行的,標記爲CountryCategory和在腳本定義如下:如果聲明VBA

Dim country As String 
Dim Category As String 
country = Sheets("Results").Range("D5").Value 
Category = Sheets("Results").Range("D6").Value 

的信息被搜索和在相對於該國的呈現搜索,並且同樣地,所述搜索運行所需的最小值是Country由用戶提供的數據庫中的國家/地區提供。

以用戶輸入的標準,則搜索通過數據在一個叫Database片和糊劑在另一片的結果稱爲Results表運行。根據搜索條件,腳本將運行If聲明中規定的幾個選項。

OPTION 1 - 用戶提供一個國家和一個類別和:

  • country存在於數據庫中,但;
  • Category不存在針對特定國家。

在這種情況下,MsgBox會彈出,說用戶提供的國家和類別的特定組合不存在於數據庫中。該消息將詢問用戶是否希望針對所提供的國家/地區的所有條目進行搜索,在這種情況下。我已經寫相應代碼如下:

finalrow = Sheets("Database").Range("A200000").End(xlUp).Row 

For i = 2 To finalrow 

    If Sheets("Database").Cells(i, 1) = country And _ 
     (Category <> "" Or Sheets("Database").Cells(i, 3) <> Category) Then 
       Dim question As Integer 
       question = MsgBox("Unfortunately, the Database has no sources regarding " & Category & " in " & country & ". Would you perhaps want to broaden your search and see all sources regarding " & country & "?", vbYesNo + vbQuestion, "Empty Sheet") 
        If question = vbYes Then 
         Sheets("Results").Range("D6").ClearContents 
         Category = Sheets("Results").Range("D6").Value 
         boolRestart = True 
        Else 
         Sheets("Results").Range("D5").ClearContents 
         Sheets("Results").Range("D6").ClearContents 
         Me.Hide 
         WelcomeForm.Show 
         Exit Sub 
        End If 

OPTION 2 - 用戶提供了country和:

  • country存在於數據庫中和;
  • 用戶還提供了一個Category存在於數據庫中爲特定國家或;
  • 用戶已經離開了Category字段爲空。

在這種情況下,搜索將運行。這是寫在腳本如下:

ElseIf Sheets("Database").Cells(i, 1) = country And _ 
     (Sheets("Database").Cells(i, 3) = Category Or Category = "") Then 

     'Copy the headers of the "Database" sheet 
     With Sheets("Database") 
      .Range("A1:I1").Copy 
     End With 
     Sheets("Results").Range("B10:J10").PasteSpecial 

     'Copy the rows of the table that match the search query 
     With Sheets("Database") 
      .Range(.Cells(i, 1), .Cells(i, 9)).Copy 
     End With 
     Sheets("Results").Range("B20000").End(xlUp).Offset(1, 0).PasteSpecial xlPasteFormulasAndNumberFormats 

    End If 

我試圖寫在幾個不同的方式腳本,但搜索引擎不斷不工作,我想。現在的情況是,當我輸入一個Country,我知道要在數據庫中,無論輸入Category以及與否,OPTION 1總是觸發。我曾試圖取出OPTION 1乾脆用選項運行只是一個If聲明2因爲是和搜索運行正常與Country填寫並與兩個CountryCategory填寫。但是,只要OPTION 1在代碼中,無論用戶輸入什麼內容,這總是選項運行。

完整的代碼是在這裏,供大家參考:

Dim country As String 'Search query country, user-inputted 
Dim Category As String 'Search query category user-inputted 
Dim finalrow As Integer 
Dim i As Integer 'row counter 
Dim ws As Worksheet 

Set ws = Sheets("Database") 

country = Sheets("Results").Range("D5").Value 
Category = Sheets("Results").Range("D6").Value 
finalrow = Sheets("Database").Range("A200000").End(xlUp).Row 

For i = 2 To finalrow 

    If Sheets("Database").Cells(i, 1) = country And _ 
     (Category <> "" Or Sheets("Database").Cells(i, 3) <> Category) Then 
       Dim question As Integer 
       question = MsgBox("Unfortunately, the Database has no sources regarding " & Category & " in " & country & ". Would you perhaps want to broaden your search and see all sources regarding " & country & "?", vbYesNo + vbQuestion, "Empty Sheet") 
        If question = vbYes Then 
         Sheets("Results").Range("D6").ClearContents 
         Category = Sheets("Results").Range("D6").Value 
         boolRestart = True 
        Else 
         Sheets("Results").Range("D5").ClearContents 
         Sheets("Results").Range("D6").ClearContents 
         Me.Hide 
         WelcomeForm.Show 
         Exit Sub 
        End If 

    ElseIf Sheets("Database").Cells(i, 1) = country And _ 
     (Sheets("Database").Cells(i, 3) = Category Or Category = "") Then 

     'Copy the headers of the "Database" sheet 
     With Sheets("Database") 
      .Range("A1:I1").Copy 
     End With 
     Sheets("Results").Range("B10:J10").PasteSpecial 

     'Copy the rows of the table that match the search query 
     With Sheets("Database") 
      .Range(.Cells(i, 1), .Cells(i, 9)).Copy 
     End With 
     Sheets("Results").Range("B20000").End(xlUp).Offset(1, 0).PasteSpecial xlPasteFormulasAndNumberFormats 

    End If 

Next I 

非常感謝您的幫助。

+0

編輯後的版本不起作用。您的原始版本將會。更好的是,在選項1中完全消除'Category'和''「''之間的比較 - 在​​這裏將'Category'與用戶輸入進行比較就足夠了。 – bobajob

+0

謝謝你的幫助!我已經這樣做了,最終結果是一樣的。無論用戶輸入如何,選項1仍然被觸發。 – franciscofcosta

回答

1

問題是,如果任何行不符合標準,您的代碼將轉到選項1,而我們希望只有在每行都不符合標準時纔會失敗。因此,我們需要對數據進行兩次掃描,第一次檢查是否有任何傳球線路(如果不是那麼我們提供清除類別),然後是另一個掃描相關數據。

試試這個:

Option Explicit 

Private Sub CommandButton1_Click() 

    Dim country As String 'Search query country, user-inputted 
    Dim Category As String 'Search query category user-inputted 
    Dim finalrow As Integer 
    Dim i As Integer 'row counter 
    Dim ws As Worksheet 
    Dim foundMatch As Boolean 
    foundMatch = False 

    Set ws = Sheets("Database") 

    country = Sheets("Results").Range("D5").Value 
    Category = Sheets("Results").Range("D6").Value 
    finalrow = Sheets("Database").Range("A200000").End(xlUp).Row 

    For i = 2 To finalrow 
     If Sheets("Database").Cells(i, 1) = country And _ 
      (Sheets("Database").Cells(i, 3) = Category Or Category = "") Then 
       foundMatch = True 
     End If 
    Next i 

    If Not foundMatch Then 
     Dim question As Integer 
     question = MsgBox("Unfortunately, the Database has no sources regarding " & Category & " in " & country & ". Would you perhaps want to broaden your search and see all sources regarding " & country & "?", vbYesNo + vbQuestion, "Empty Sheet") 
      If question = vbYes Then 
       Sheets("Results").Range("D6").ClearContents 
       Category = Sheets("Results").Range("D6").Value 
      Else 
       Sheets("Results").Range("D5").ClearContents 
       Sheets("Results").Range("D6").ClearContents 
       Me.Hide 
       WelcomeForm.Show 
       Exit Sub 
      End If 
    End If 

    For i = 2 To finalrow 
     If Sheets("Database").Cells(i, 1) = country And _ 
      (Sheets("Database").Cells(i, 3) = Category Or Category = "") Then 
       'Copy the headers of the "Database" sheet 
       With Sheets("Database") 
        .Range("A1:I1").Copy 
       End With 
       Sheets("Results").Range("B10:J10").PasteSpecial 

       'Copy the rows of the table that match the search query 
       With Sheets("Database") 
        .Range(.Cells(i, 1), .Cells(i, 9)).Copy 
       End With 
       Sheets("Results").Range("B20000").End(xlUp).Offset(1, 0).PasteSpecial xlPasteFormulasAndNumberFormats 
     End If 
    Next i 

End Sub 
+0

謝謝!這工作! – franciscofcosta

1

我想你應該在三個獨立的子程序劃分代碼: - 當用戶觸發搜索的第一個會跑的話,就必須檢查是否country有(給錯誤消息,如果不是)一個有效的值,然後檢查是否Category有一個值,如果它有值,轉到第二個子程序,如果它是空的,轉到第三個子程序; - 第二個子程序必須獲得countryCategory變量的值並返回預期結果; - 第三個子程序只能得到country變量並返回預期的結果。

你可以把模塊的開頭兩個變量(之前的任何Sub和使用Private代替Dim)離開他們到模塊中的任何子程序訪問,或者你可以創建參數,子程序在那裏你可以值傳遞給另一個Sub,但不允許它們訪問該模塊中的所有Sub。我更喜歡第二種選擇。如果你不知道如何將參數傳遞到另一個模塊,它是一個例子:

Sub QueryCountryAndCategory (QCountry as String, QCategory as String) 

在這種SubQCountryQCategory是變量,將只在該模塊是可訪問的,它會接收傳遞的值通過來電顯示子程序,這樣的事情(使用變量):

QueryCountryAndCategory(country, Category) 

或者這樣:

QueryCountryAndCategory(QCountry:=country, QCategory:=Category) 

請記住,長代碼難以維護並且難以測試。當你的代碼變長時,總是考慮將它分成一些Sub s或Function s(它會返回一個值)。測試也更容易,因爲您可以單獨運行每個Sub以查看它是否正常工作。

0

(Category <> "" Or Sheets("Database").Cells(i, 3) <> Category) Then更換ORAND

,辦理入住手續必須考慮

  1. category不是空的,
  2. category不發現

中頻工作的方式是,它總是會觸發如果任

  1. category心不是空(因此,如果您在category輸入任何內容,它將匹配在這裏)
  2. category不匹配(如果category爲空,但它實際上有任何內容)