Pergunta

Eu preciso de uma função que leva o nome de um símbolo como uma string e retorna se esse símbolo já está definido. A função ValueQ está perto, mas ele retorna False para nomes de função. Além disso, leva símbolos em vez de strings.

Exemplos:

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:. Graças a Pillsy por apontar a necessidade de verificar para ambos os DownValues ??e subvalores

Foi útil?

Solução 2

Eu calçada isso juntos, o que parece funcionar:

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

Esperemos que há uma solução mais bonita.

PS:. Graças a Pillsy por apontar a necessidade de verificar para ambos os DownValues ??e subvalores

Outras dicas

Eu acho Nomes deve fazer o truque:

Nomes [ "string"] dá uma lista do nomes de símbolos que correspondem a string.

Se Names [ "foo"] retorna {}, então não deve haver definições para foo, caso contrário, ele deve retornar { "foo"}. Portanto, sua função 'definido' pode ser feito como:

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

Para símbolos, pelo menos, porque isso não funciona para "7", desde 7 não é um símbolo. Você poderia lidar com este caso separadamente, por exemplo, com NumberQ.

Além disso, você pode usar o símbolo para fazer um símbolo a partir de uma string (útil para gerar automaticamente símbolos) e definição de verificar as definições de um símbolo.

Simbolo [ "nome"] refere-se a um símbolo com o nome especificado.

A definição [símbolo] imprime como o definições dadas para um símbolo.

Editar : Melhor do que olhar para o que Nomes retornos, NameQ [ "nome"] informa se um determinado nome existe. continua a não dizer se o símbolo tem uma definição explícita, porém, apenas que ele foi mencionado.

Você pode usar DownValues para ver se você tem "funções" associados a um símbolo. Isto irá funcionar para definições como

f[x_, y_] := x + y

ou

g[3] = 72 * a;

Não vai trabalhar para coisas exóticas como

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

mas a maioria das pessoas não vão pensar nisso como a definição de uma função de qualquer maneira. Se você deseja verificar a existência de uma definição de função, você precisa converter o nome de uma expressão (e verifique se ele está envolvido em Hold quando você faz!). Aqui está uma função razoavelmente robusto que verifica tanto DownValues e SubValues:

functionNameQ[name_String] := 
    With[{ hSymbol = ToExpression[name, InputForm, Hold] },
        MatchQ[hSymbol, Hold[_Symbol]] &&
            ((DownValues @@ hName) =!= {} || (SubValues @@ hName) =!= {})];
defined[str_] := Not[ToString[FullDefinition[str]] === ""]
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top