¿Hay un JavaScript equivalente de Java s' class.getName()
?
javascript
Ewen Cartwright
fuente
fuente
Respuestas:
No se .
Actualización de ES2015 : el nombre de
class Foo {}
esFoo.name
. El nombre dething
la clase, independientemente delthing
tipo, esthing.constructor.name
. Los constructores incorporados en un entorno ES2015 tienen laname
propiedad correcta ; por ejemplo(2).constructor.name
es"Number"
.Pero aquí hay varios hacks que se caen de una forma u otra:
Aquí hay un truco que hará lo que necesita: tenga en cuenta que modifica el prototipo del Objeto, algo que la gente desaprueba (generalmente por una buena razón)
Ahora, todos sus objetos tendrán la función
getName()
, que devolverá el nombre del constructor como una cadena. He probado estoFF3
yIE7
no puedo hablar de otras implementaciones.Si no desea hacer eso, aquí hay una discusión sobre las diversas formas de determinar los tipos en JavaScript ...
Recientemente actualicé esto para que sea un poco más exhaustivo, aunque difícilmente sea eso. Correcciones bienvenidas ...
Usando la
constructor
propiedad ...Cada uno
object
tiene un valor para suconstructor
propiedad, pero dependiendo de cómoobject
se construyó y de qué quiere hacer con ese valor, puede ser útil o no.En términos generales, puede usar la
constructor
propiedad para probar el tipo de objeto de la siguiente manera:Entonces, eso funciona lo suficientemente bien para la mayoría de las necesidades. Dicho eso ...
Advertencias
No funciona en absoluto en muchos casos
Este patrón, aunque roto, es bastante común:
Objects
construido víanew Thingy
tendrá unaconstructor
propiedad que apunta aObject
, noThingy
. Entonces caemos desde el principio; simplemente no puedes confiarconstructor
en una base de código que no controlas.Herencia múltiple
Un ejemplo en el que no es tan obvio es usar la herencia múltiple:
Las cosas ahora no funcionan como es de esperar que:
Por lo tanto, puede obtener resultados inesperados si la
object
prueba tiene unobject
conjunto diferente como talprototype
. Hay formas de evitar esto fuera del alcance de esta discusión.Hay otros usos para la
constructor
propiedad, algunos interesantes, otros no tanto; por ahora no profundizaremos en esos usos ya que no es relevante para esta discusión.No funcionará entre marcos y ventanas cruzadas
El uso
.constructor
para la verificación de tipo se interrumpirá cuando desee verificar el tipo de objetos que provienen de diferenteswindow
objetos, por ejemplo, de un iframe o una ventana emergente. Esto se debe a que hay una versión diferente de cada tipo de núcleoconstructor
en cada 'ventana', es decirUsar el
instanceof
operador ...El
instanceof
operador también es una forma limpia de probar elobject
tipo, pero tiene sus propios problemas potenciales, al igual que laconstructor
propiedad.Pero
instanceof
no funciona para valores literales (porque los literales no lo sonObjects
)Los literales deben estar envueltos en un
Object
parainstanceof
que funcionen, por ejemploLa
.constructor
comprobación funciona bien para los literales porque la.
invocación del método envuelve implícitamente los literales en su tipo de objeto respectivo¿Por qué dos puntos para los 3? Porque Javascript interpreta el primer punto como un punto decimal;)
No funcionará entre marcos y ventanas cruzadas
instanceof
tampoco funcionará en diferentes ventanas, por la misma razón que laconstructor
verificación de propiedad.Usar la
name
propiedad de laconstructor
propiedad ...No funciona en absoluto en muchos casos
De nuevo, ver arriba; Es bastante común
constructor
que esté completamente equivocado e inútil.NO funciona en <IE9
El uso
myObjectInstance.constructor.name
le dará una cadena que contiene el nombre de laconstructor
función utilizada, pero está sujeta a las advertencias sobre laconstructor
propiedad que se mencionó anteriormente.Para IE9 y superior, puede parchear en soporte :
Versión actualizada del artículo en cuestión. Esto se agregó 3 meses después de que se publicó el artículo, esta es la versión recomendada para usar por el autor del artículo Matthew Scharley. Este cambio se inspiró en los comentarios que señalaban posibles dificultades en el código anterior.
Usando Object.prototype.toString
Resulta que, como se detalla en esta publicación , puede usar
Object.prototype.toString
la implementación genérica y de bajo nivel detoString
para obtener el tipo para todos los tipos integradosSe podría escribir una función auxiliar breve como
para eliminar el cruft y obtener solo el nombre del tipo
Sin embargo, regresará
Object
para todos los tipos definidos por el usuario.Advertencias para todos ...
Todos estos están sujetos a un problema potencial, y esa es la cuestión de cómo se construyó el objeto en cuestión. Aquí hay varias formas de construir objetos y los valores que devolverán los diferentes métodos de verificación de tipos:
Si bien no todas las permutaciones están presentes en este conjunto de ejemplos, es de esperar que haya suficientes para darle una idea acerca de lo desordenado que podrían ser las cosas según sus necesidades. No asumas nada, si no entiendes exactamente lo que estás buscando, puedes terminar con el descifrado del código donde no esperas que lo hagas debido a la falta de asimilar las sutilezas.
NOTA:
La discusión sobre el
typeof
operador puede parecer una omisión evidente, pero realmente no es útil para ayudar a identificar si un tipoobject
es dado, ya que es muy simplista. Comprender dóndetypeof
es útil es importante, pero actualmente no siento que sea terriblemente relevante para esta discusión. Sin embargo, mi mente está abierta al cambio. :)fuente
constructor
método del objeto (ya sea con.toString()
o.name
) no funcionará si su Javascript se ha minimizado con una herramienta como uglify o la canalización de activos de Rails. La minificación cambia el nombre del constructor, por lo que terminará con nombres de clase incorrectos comon
. Si se encuentra en este escenario, es posible que desee definir manualmente unaclassName
propiedad en sus objetos y usarla en su lugar.La respuesta de Jason Bunting me dio una pista suficiente para encontrar lo que necesitaba:
Entonces, por ejemplo, en el siguiente fragmento de código:
myInstance.constructor.name
Volvería"MyObject"
.fuente
function getType(o) { return o && o.constructor && o.constructor.name }
Un pequeño truco que uso:
fuente
class Square
, el nombre esSquare.name
/ enMySquare.constructor.name
lugar deSquare.prototype.name
; al ponername
la función de constructor no contamina el prototipo ni ninguna instancia, pero es accesible desde cualquiera de ellos.Actualizar
Para ser precisos, creo que OP solicitó una función que recupere el nombre del constructor para un objeto en particular. En términos de Javascript,
object
no tiene un tipo pero es un tipo de y en sí mismo . Sin embargo, diferentes objetos pueden tener diferentes constructores .Nota: el siguiente ejemplo está en desuso.
Una publicación de blog vinculada por Christian Sciberras contiene un buen ejemplo sobre cómo hacerlo. Es decir, al extender el prototipo de objeto:
fuente
test.getClassName()
vsgetClassName.apply(test)
.Usando Object.prototype.toString
Resulta que, como se detalla en esta publicación, puede usar Object.prototype.toString, la implementación genérica y de bajo nivel de toString, para obtener el tipo para todos los tipos integrados
Se podría escribir una función auxiliar breve como
fuente
.slice()
:Object.prototype.toString.call(obj).slice( 8, -1 );
Aquí hay una solución que se me ocurrió que resuelve las deficiencias de instanceof. Puede verificar los tipos de un objeto desde ventanas cruzadas y marcos cruzados y no tiene problemas con los tipos primitivos.
isInstance requiere dos parámetros: un objeto y un tipo. El verdadero truco de cómo funciona es que comprueba si el objeto proviene de la misma ventana y, si no, obtiene la ventana del objeto.
Ejemplos:
El argumento tipo también puede ser una función de devolución de llamada que devuelve un constructor. La función de devolución de llamada recibirá un parámetro que es la ventana del objeto proporcionado.
Ejemplos:
Una cosa a tener en cuenta es que IE <9 no proporciona el constructor en todos los objetos, por lo que la prueba anterior para NodeList devolvería falso y también un isInstance (alerta, "Función") devolvería falso.
fuente
En realidad estaba buscando algo similar y me encontré con esta pregunta. Así es como obtengo tipos: jsfiddle
fuente
Deberías usar
somevar.constructor.name
como:fuente
Úselo
constructor.name
cuando pueda y regex funcione cuando yo no pueda.fuente
La función kind () de Agave.JS devolverá:
Funciona en todos los objetos JS y primitivas, independientemente de cómo se crearon , y no tiene ninguna sorpresa. Ejemplos:
Números
Yaya
Instrumentos de cuerda
Booleanos
Matrices
Objetos
fechas
Las funciones
indefinido
nulo
fuente
Puede usar el
instanceof
operador para ver si un objeto es una instancia de otro, pero como no hay clases, no puede obtener un nombre de clase.fuente
instanceof
solo comprueba si un objeto hereda de otros objetos. Por ejemplo, un simple[]
hereda de Array, pero Array también hereda de Object. Como la mayoría de los objetos tienen múltiples niveles de herencia, encontrar el prototipo más cercano es una mejor técnica. Vea mi respuesta de cómo.Aquí hay una implementación basada en la respuesta aceptada :
Solo usamos la propiedad constructor cuando no tenemos otra opción.
fuente
Puede usar el operador "instanceof" para determinar si un objeto es una instancia de una determinada clase o no. Si no conoce el nombre del tipo de un objeto, puede usar su propiedad de constructor. La propiedad constructora de los objetos, es una referencia a la función que se utiliza para inicializarlos. Ejemplo:
Ahora c1.constructor es una referencia a la
Circle()
función. También puede usar eltypeof
operador, pero eltypeof
operador muestra información limitada. Una solución es usar eltoString()
método del objeto global Object. Por ejemplo, si tiene un objeto, por ejemplo, myObject, puede usar eltoString()
método del objeto global para determinar el tipo de la clase de myObject. Utilizar este:fuente
Di que tienes
var obj;
Si solo desea el nombre del tipo de obj, como "Objeto", "Matriz" o "Cadena", puede usar esto:
fuente
Lo más cercano que puede obtener es
typeof
, pero solo devuelve "objeto" para cualquier tipo de tipo personalizado. Para aquellos, ver Jason Bunting .Editar, Jason ha eliminado su publicación por alguna razón, así que solo usa la
constructor
propiedad de Object .fuente
Si alguien estaba buscando una solución que funciona con jQuery, aquí está el código wiki ajustado (el original rompe jQuery).
fuente
getName
y se cae.Lodash tiene muchos métodos isMe, así que si estás usando Lodash, tal vez un mixin como este pueda ser útil:
Agrega un método a lodash llamado "identificar" que funciona de la siguiente manera:
Plunker: http://plnkr.co/edit/Zdr0KDtQt76Ul3KTEDSN
fuente
Ok, amigos, he estado construyendo lentamente un método catch all para esto durante algunos años, ¡jaja! El truco es:
Para ver un ejemplo (o para ver cómo solucioné el problema), mire el siguiente código en github: https://github.com/elycruz/sjljs/blob/master/src/sjl/sjl.js y busque:
classOf =
,classOfIs =
Y odefineSubClass =
(sin las comillas invertidas ( `)).Como puede ver, tengo algunos mecanismos para forzarme
classOf
a darme siempre el nombre del tipo de clases / constructores, independientemente de si es una clase primitiva, definida por el usuario, un valor creado usando un constructor nativo, Null, NaN, etc. Por cada valor de JavaScript obtendré su nombre de tipo único de laclassOf
función. Además, puedo pasar a constructores realessjl.classOfIs
para verificar el tipo de un valor, ¡además de poder pasar su nombre de tipo también! Así por ejemplo:`` // ¡Por favor, perdona los largos espacios de nombres! No tenía idea del impacto hasta después de usarlos por un tiempo (apestan jaja)
`` `
Si está interesado en leer más sobre cómo uso la configuración mencionada anteriormente, eche un vistazo al repositorio: https://github.com/elycruz/sjljs
También libros con contenido sobre el tema: - "Patrones JavaScript" de Stoyan Stefanov. - "Javascript - La guía definitiva". por David Flanagan. - y muchos otros .. (buscar le` web).
También puede probar rápidamente las características de las que estoy hablando aquí: - http://sjljs.elycruz.com/0.5.18/tests/for-browser/ (también la ruta 0.5.18 en la url tiene las fuentes de github allí menos los node_modules y tal).
¡Feliz codificación!
fuente
¡Bastante simple!
fuente
Uso
class.name
. Esto también funciona confunction.name
.fuente
class
y no instancia.