2017-02-09 17 views
0

B9に値が入るまでこのコードでサブをループしようとしています。 while文を含めるまでは、私が下手に何をしているのか不明です。Excell whileループでサブ呼び出しを繰り返す

Private Sub CommandButton2_Click() 

Range("B5:B18").ClearContents 

If [D2] = [R15] Then 
    Do While IsEmpty("B9") = True 
     Randomname 
    Loop 
End If 

また、おそらく関連性の高いサブコードを投稿してください。 サブは、私が見つけて自分のニーズに合わせて変更したコードに基づいたランダムな名前選択ツールです。 2つの範囲を比較し、まだ使用されていないソース範囲の名前を一度に1つずつ取り出します。

Sub Randomname() 
Dim source, destination As Range 

Set source = ActiveSheet.Range("L15:L28") 
Set destination = ActiveSheet.Range("B5:B18") 
ReDim randoms(1 To source.Rows.Count) 
destrow = 0 
For i = 1 To destination.Rows.Count 
    If destination(i) = "" Then: destrow = i: Exit For 
Next i 
If destrow = 0 Then: MsgBox "no more room in destination range": Exit Sub 
For i = 1 To UBound(randoms): randoms(i) = Rnd(): Next i 
ipick = 0: tries = 0 
Do While ipick = 0 And tries < UBound(randoms) 
    tries = tries + 1 
    minrnd = WorksheetFunction.Min(randoms) 
    For i = 1 To UBound(randoms) 
    If randoms(i) = minrnd Then 
     picked_before = False 
     For j = 1 To destrow - 1 
     If source(i) = destination(j) Then: picked_before = True: randoms(i) = 2: Exit For 
     Next j 
     If Not picked_before Then: ipick = i 
     Exit For 
    End If 
    Next i 
Loop 
If ipick = 0 Then: MsgBox "no more unique name possible to pick": Exit Sub 
destination(destrow) = source(ipick) 
End Sub 
+2

IsEmpty( "B9") 'は常にfalseを返します。あなたはおそらく 'IsEmpty([B9])'を探しています。 – Comintern

+0

あなたは私に正しい方向に考えさせることができました。 Do Is Ismpty(範囲( "B9")。値)= True ありがとうございます。 – user3107457

+0

@ user3107457 IsEmpty(Range( "B9")。Value)= TrueはIsEmpty([B9])と同じです。 ( '= True'部分は冗長です。なぜなら、それ自身が' True'なら 'True'に、' Range( "B9").Value'は 'B9 ''のショートカットです)。 – YowE3K

答えて

0

あなたの構文はあなたが

If destination(i) = "" Then: destrow = i: Exit For 

を持ってどこが同じ行に複数のコマンドを実行するために、コロンを使用する場合は、可能

If desination(i) = "" Then 
    destrow = i 
    Exit For 
End If 

とオフの方が良いだろう間違っているように見えます構文が正しいことを確認してください。私は自分のコードを読みやすくするために、個人的には各コマンドを自分の行に保存する方が好きです。これはループで特に重要です。

最後に、thenステートメントで1つのコマンドだけを実行する場合は、コロンを使用せずにthenの後に入力することができます。それ以外の場合は、ifブロックを使用します。

例えば

If True = True then msgbox "True" 

または複数のコマンドのための

If True = True Then 
    msgbox "True" 
    msgbox "Not False" 
End if 

それはより安全であり、それを理解することはあなたのコードが簡単になります。

+1

'if destination(i)=" "Then:destrow = i:Exit For'はうまく動作します。それは地獄のように醜いですが、それはコンパイルされ、実行されます。 – Comintern

+0

私はそれがうまくコンパイルされ、複数の行(End Ifが必要です)として読み込まないことに驚いています。あなたが指摘したように、まだ非常に醜い。また、読みにくい。 –

+0

単一行の 'If'ステートメント内でのコロンの使用についての興味深い議論については、[この質問と回答](http://stackoverflow.com/q/41983020/6535336)を参照してください。 – YowE3K

関連する問題