Como obter o nome do object de class como uma string em JavaScript?

Digamos que eu instancie um object em Javascript assim:

var myObj = new someObject(); 

Agora, é possível obter o nome do object var como string 'myObj' dentro de um dos methods de class?


Detalhes adicionais (editados):

A razão pela qual eu gostaria de obter o nome da variável que contém referência ao object é que meu novo myObj criaria um novo DIV clicável na página que precisaria chamar uma function myObj.someFunction() . Ao inserir o novo DIV , preciso saber o nome da variável que contém referência ao object. Existe talvez uma maneira melhor de fazer isso?


Você está certo, desculpe pela confusão na terminologia.

A razão pela qual eu gostaria de obter o nome da variável que contém referência ao object é que meu novo myObj criaria um novo DIV clicável na página que precisaria chamar uma function myObj.someFunction (). Ao inserir o novo DIV, preciso saber o nome da variável que contém referência ao object. Existe talvez uma maneira melhor de fazer isso?

   

Shog9 está certo de que isso não faz muito sentido perguntar, já que um object poderia ser referido por múltiplas variables. Se você realmente não se importa com isso, e tudo que você quer é encontrar o nome de uma das variables ​​globais que se referem àquele object, você pode fazer o seguinte hack:

 function myClass() { this.myName = function () { // search through the global object for a name that resolves to this object for (var name in this.global) if (this.global[name] == this) return name } } // store the global object, which can be referred to as this at the top level, in a // property on our prototype, so we can refer to it in our object's methods myClass.prototype.global = this // create a global variable referring to an object var myVar = new myClass() myVar.myName() // returns "myVar" 

Observe que esse é um hack feio e não deve ser usado no código de produção. Se houver mais de uma variável referindo-se a um object, você não poderá dizer qual delas obterá. Ele só pesquisará as variables ​​globais, portanto não funcionará se uma variável for local para uma function. Em geral, se você precisar nomear algo, você deve passar o nome para o construtor ao criá-lo.

edit : Para responder ao seu esclarecimento, se você precisar se referir a algo de um manipulador de events, você não deve estar se referindo a ele pelo nome, mas sim adicionar uma function que se refere diretamente ao object. Aqui está um exemplo rápido que eu mostrei algo semelhante, eu acho, ao que você está tentando fazer:

 function myConstructor () { this.count = 0 this.clickme = function () { this.count += 1 alert(this.count) } var newDiv = document.createElement("div") var contents = document.createTextNode("Click me!") // This is the crucial part. We don't construct an onclick handler by creating a // string, but instead we pass in a function that does what we want. In order to // refer to the object, we can't use this directly (since that will refer to the // div when running event handler), but we create an anonymous function with an // argument and pass this in as that argument. newDiv.onclick = (function (obj) { return function () { obj.clickme() } })(this) newDiv.appendChild(contents) document.getElementById("frobnozzle").appendChild(newDiv) } window.onload = function () { var myVar = new myConstructor() } 

Resposta curta: Não. MyObj não é o nome do object, é o nome de uma variável que contém uma referência ao object – você pode ter qualquer número de outras variables ​​contendo uma referência ao mesmo object.

Agora, se é o seu programa, então você faz as regras: se você quer dizer que qualquer object será referenciado apenas por uma variável, sempre, e diligentemente reforce isso em seu código, então apenas defina uma propriedade no object com o código. nome da variável.

Dito isto, duvido que o que você está pedindo é realmente o que você realmente quer. Talvez descreva seu problema um pouco mais detalhadamente …?


Pedantry: JavaScript não tem classs. someObject é uma function construtora. Dada uma referência a um object, você pode obter uma referência à function que a criou usando a propriedade constructor .


Em resposta aos detalhes adicionais que você forneceu:

A resposta que você está procurando pode ser encontrada aqui: Escopo de Retorno de Chamadas em JavaScript (e em resposta a inúmeras outras perguntas sobre SO – é um ponto comum de confusão para aqueles que são novos em JS). Você só precisa envolver a chamada no membro do object em um fechamento que preserva o access ao object de contexto.

Você pode fazer isso convertendo pelo construtor para uma string usando .toString () :

 function getObjectClass(obj){ if (typeof obj != "object" || obj === null) return false; else return /(\w+)\(/.exec(obj.constructor.toString())[1];} 

Você pode conseguir seu objective usando-o em uma function e examinando a origem da function com toString() :

 var whatsMyName; // Just do something with the whatsMyName variable, no matter what function func() {var v = whatsMyName;} // Now that we're using whatsMyName in a function, we could get the source code of the function as a string: var source = func.toString(); // Then extract the variable name from the function source: var result = /var v = (.[^;]*)/.exec(source); alert(result[1]); // Should alert 'whatsMyName'; 

Se você não quiser usar um construtor de function como na resposta de Brian, você pode usar Object.create (): –

 var myVar = { count: 0 } myVar.init = function(n) { this.count = n this.newDiv() } myVar.newDiv = function() { var newDiv = document.createElement("div") var contents = document.createTextNode("Click me!") var func = myVar.func(this) newDiv.addEventListener ? newDiv.addEventListener('click', func, false) : newDiv.attachEvent('onclick', func) newDiv.appendChild(contents) document.getElementsByTagName("body")[0].appendChild(newDiv) } myVar.func = function (thys) { return function() { thys.clickme() } } myVar.clickme = function () { this.count += 1 alert(this.count) } myVar.init(2) var myVar1 = Object.create(myVar) myVar1.init(55) var myVar2 = Object.create(myVar) myVar2.init(150) // etc 

Estranhamente, eu não consegui fazer o acima funcionar usando newDiv.onClick, mas funciona com newDiv.addEventListener / newDiv.attachEvent.

Como o Object.create é novo, inclua o seguinte código do Douglas Crockford para navegadores mais antigos, incluindo o IE8.

 if (typeof Object.create !== 'function') { Object.create = function (o) { function F() {} F.prototype = o return new F() } } 

Como uma situação mais elementar, seria legal se this tivesse uma propriedade que pudesse referenciar sua variável de referência ( heads ou tails ), mas infelizmente ela apenas referencia a instanciação do novo object coinSide .

 javascript: /* it would be nice but ... a solution NOT! */ function coinSide(){this.ref=this}; /* can .ref be set so as to identify it's referring variable? (heads or tails) */ heads = new coinSide(); tails = new coinSide(); toss = Math.random()<0.5 ? heads : tails; alert(toss.ref); alert(["FF's Gecko engine shows:\n\ntoss.toSource() is ", toss.toSource()]) 

que sempre exibe

 [object Object] 

e o motor Gecko do Firefox mostra:

 toss.toSource() is ,#1={ref:#1#} 

Obviamente, neste exemplo, para resolver #1 e, portanto, toss , é simples o suficiente para testar toss==heads and toss==tails . Esta questão, que é realmente perguntando se o javascript tem um mecanismo call-by-name , motiva a consideração da contraparte, existe um mecanismo de call-by-value para determinar o valor ACTUAL de uma variável? O exemplo demonstra que os "valores" de ambas as heads e tails são idênticos, mas o alert(heads==tails) é false .

A auto-referência pode ser coagida da seguinte forma:
(evitando a caça ao espaço de objects e possíveis ambigüidades, conforme observado no nome do object da class How to get class as a string in Javascript? )

 javascript: function assign(n,v){ eval( n +"="+ v ); eval( n +".ref='"+ n +"'" ) } function coinSide(){}; assign("heads", "new coinSide()"); assign("tails", "new coinSide()"); toss = Math.random()<0.5 ? heads : tails; alert(toss.ref); 

para exibir heads ou tails .

Talvez seja um anátema para a essência do design de linguagem do Javascript, como uma linguagem funcional de prototipagem interpretada, ter resources como primitivos.

Uma consideração final:

  javascript: item=new Object(); refName="item"; deferAgain="refName"; alert([deferAgain,eval(deferAgain),eval(eval(deferAgain))].join('\n')); 

então, como estipulado ...

 javascript: function bindDIV(objName){ return eval( objName +'=new someObject("'+objName+'")' ) }; function someObject(objName){ this.div="\n
clickable DIV
\n"; this.someFunction=function(){alert(['my variable object name is ',objName])} }; with(window.open('','test').document){ /* see above hiccup */ write(''+ bindDIV('DIVobj1').div+ bindDIV('DIV2').div+ (alias=bindDIV('multiply')).div+ 'an aliased DIV clone'+multiply.div+ ''); close(); }; void (0);

Existe uma maneira melhor ... ?

"melhor" como mais fácil? Mais fácil de programar? Mais fácil de entender? Mais fácil como na execução mais rápida? Ou é como em " ... e agora para algo completamente diferente "?

Imediatamente após o object ser instantâneo, você pode append uma propriedade, diga o name , ao object e atribuir o valor da string que você espera a ele:

 var myObj = new someClass(); myObj.name="myObj"; document.write(myObj.name); 

Alternativamente, a atribuição pode ser feita dentro dos códigos da class, ou seja,

 var someClass = function(P) { this.name=P; // rest of the class definition... }; var myObj = new someClass("myObj"); document.write(myObj.name); 

Algum tempo atrás, eu usei isso.

Talvez você possa tentar:

 +function(){ var my_var = function get_this_name(){ alert("I " + this.init()); }; my_var.prototype.init = function(){ return my_var.name; } new my_var(); }(); 

Pop um Alerta : "I get_this_name" .

Isso é muito antigo, mas eu encontrei essa pergunta pelo Google, então talvez essa solução possa ser útil para outras pessoas.

 function GetObjectName(myObject){ var objectName=JSON.stringify(myObject).match(/"(.*?)"/)[1]; return objectName; } 

Ele apenas usa o analisador JSON e o regex do navegador sem sobrecarregar o DOM ou seu object.