0

Excel の VBA で特定の範囲を並べ替える関数を作成する必要があります。(バブルソート)私は次のことをしました:

Function MySort(M2 As Range)

    Dim r As Integer
    r = M2.Rows.Count

    Dim M1 as range
    M1 = M2

    Dim buffer

    For i = 0 To r
        For j = i To r

            If (M1.Item(i, 0) > M1.Item(j, 0)) Then

                buffer = M1.Item(i, 0)
                M1.Item(i, 0) = M1.Item(j, 0)
                M1.Item(j, 0) = buffer

            End If

        Next j
    Next i

    MySort = M1

End Function

問題 :

  • 「#VALUE」を返します
  • Range を配列に変換しようとしました
  • M2 を M1 にキャストしない場合、関数はソートされていないリストを返します
  • 基底1と基底0で試しました

次の例で強調されている主な問題を特定したと思います。

Function TestArray(M1 As Range)

    r = M1.Rows.Count

    Dim M2 As Range

    Dim M3()
    ReDim M3(r)

    M3 = M1
    M2 = M1

    TestArray = M3(0, 0) ' or M2.item(0, 0)

End Function

この関数は「#VALUE」を返します。

M2.item(0, 0) が "#VALUE" を返すのはなぜですか? 同じ配列/ Range の 2 つの値を比較する正しい方法は何ですか?

4

2 に答える 2

2

さて、この行:

Dim M1 as range

範囲変数への参照を保持できる空の変数を作成しています

M1 = M2

実際には

Let M1.Value = M2.Value

しかし、M1 は Nothing (他の言語では null) であるため、そのプロパティの 1 つに適切に割り当てることはできません。したがって、UDF はその行でエラーをスローして終了します。オブジェクトや何かをキャストしていません。そもそも M1 を必要としたり使用したりすべきではありません。必要なのは M2 だけです。

さらに、この行:

M1.Item(i, 0) = M1.Item(j, 0)

次のようになります。

M1.Cells(i, 0) = M1.Cells(j, 0)

ただし、UDF では機能しません。Excel セルの数式から呼び出す関数は、他のセルの内容を変更することはできません。これは Excel では大したことではありません。UDF は他のセルのみを読み取り、値を返すことができます。それでおしまい。他のセルを変更したい場合は、UDF としてではなく、マクロとして呼び出す必要があります。

編集:さらに読むための参照

UDF の作成とその制限については、こちら を参照してください。Let と Set の違いについては、こちらをご覧
ください。ここここで 範囲オブジェクトについて読むことも役立つかもしれません。

于 2013-09-30T17:54:50.110 に答える