3

シンボルの名前を文字列として受け取り、そのシンボルが既に定義されているかどうかを返す関数が必要です。関数ValueQは近いですが、関数名に対して False を返します。また、文字列ではなく記号を取ります。

例:

defined["N"] --> True (predefined function N)
defined["x"] --> False
x = 7;
defined["x"] --> True (x is now defined)
defined["7"] --> True (7 is a number)
f[x_] := 2x
defined["f"] --> True (f has DownValues)
g[x_][y_] := x+y
defined["g"] --> True (g has SubValues)

PS: DownValues と SubValues の両方をチェックする必要があることを指摘してくれた Pillsy に感謝します。

4

4 に答える 4

3

私はこれを一緒に石畳にしましたが、うまくいくようです:

defined[s_] := ToExpression["ValueQ[" <> s <> "]"] || 
               Head@ToExpression[s] =!= Symbol || 
               ToExpression["Attributes[" <> s <> "]"] =!= {} ||
               ToExpression["DownValues[" <> s <> "]"] =!= {} ||
               ToExpression["SubValues[" <> s <> "]"] =!= {}

うまくいけば、よりきれいな解決策があります。

PS: DownValues と SubValues の両方をチェックする必要があることを指摘してくれた Pillsy に感謝します。

于 2009-09-18T19:50:04.777 に答える
2

私は名前がトリックを行うべきだと思います:

Names["string"] は文字列にマッチするシンボルの名前のリストを与える.

Names["foo"] が {} を返す場合、foo の定義はなく、そうでない場合は {"foo"} を返す必要があります。したがって、「定義済み」の関数は次のように実行できます。

defined[str_] := Names[str] != {}

少なくとも記号については、これは「7」では機能しないためです。7 は記号ではないためです。このケースは、たとえば NumberQ を使用して個別に処理できます。

また、Symbol を使用して文字列からシンボルを作成し (シンボルの自動生成に役立ちます)、Definition を使用してシンボルの定義を確認することもできます。

Symbol["name"] は、指定された名前のシンボルを参照します。

Definition[symbol] は、シンボルに与えられた定義として出力します。

編集: Names が返すものを見るよりも、 NameQ["name"] は、指定された名前が存在するかどうかを示します。ただし、シンボルに明示的な定義があるかどうかはわかりませんが、言及されているだけです。

于 2009-09-18T19:47:29.393 に答える
2

DownValuesシンボルに関連付けられた「関数」があるかどうかを確認するために使用できます。これは、次のような定義で機能します

f[x_, y_] := x + y

また

g[3] = 72 * a;

次のようなエキゾチックなものには機能しません

h[a_][b] = "gribble";

しかし、ほとんどの人はそれを関数の定義とは考えません。関数定義の存在を確認したい場合は、名前を式に変換する必要があります (そして、そのHold際にラップされていることを確認してください!)。DownValuesと の両方をチェックするかなり堅牢な関数を次に示しますSubValues

functionNameQ[name_String] := 
    With[{ hSymbol = ToExpression[name, InputForm, Hold] },
        MatchQ[hSymbol, Hold[_Symbol]] &&
            ((DownValues @@ hName) =!= {} || (SubValues @@ hName) =!= {})];
于 2009-09-19T02:23:56.260 に答える