2012-03-16 12 views
6

Cuando ejecuto el siguiente código me dicen que esa conversación no es una función. ¿Por qué?¿No es una función?

function cat(name) { 
    talk = function() { 
     alert(" say meeow!") 
    } 
} 

cat("felix"); 
cat.talk() 
+0

¿Intentaba hacer una clase 'cat', o definía un objeto que tenía una función talk? –

Respuesta

9

Lo que estamos tratando de hacer es crear un objeto para el cual la función es un constructor, pero lo que el código está haciendo realidad está estableciendo la variable de talk a una función. ¿Quieres:

function cat(name) { 
    this.talk = function() { 
     alert(" say meeow!") 
    } 
} 

var myCat = new cat("felix"); 
myCat.talk() 

edición:

Relevante charla Javascript tecnología: http://www.youtube.com/watch?v=ljNi8nS5TtQ

Él habla de la construcción de objetos con funciones a unos 30 minutos en el Código él mensajes es:.

function Circle(radius){ 
    this.radius = radius; 
    this.area = function(){ 
     return this.radius * this.radius * Math.PI; 
    }; 
} 
var instance = {}; 
Circle.call(instance, 5); 
instance.area(); // ==> 78.5398 
var instance2 = new Circle(5); 
instance2.area() // ==> 78.5398 
instance instanceof Circle // ==> false 
instance2 instanceof Circle // ==> true 

Y la cotización relevante:

La nueva palabra clave es simplemente una abreviatura que está diciendo "hacer un nuevo objeto y llama al constructor en él ... la nueva palabra clave no tiene otro significa"

En otras palabras, él está diciendo que cuando utilizando la palabra clave new, está definiendo su variable como un objeto y llamando a la función en el contexto de ese objeto (this apunta a su objeto).

Lo que hace la palabra clave new es establecer el prototipo del objeto recién creado para el prototipo del constructor. Así que si hacemos:

function Circle(radius){ 
    this.radius = radius; 
    this.area = function(){ 
     return this.radius * this.radius * Math.PI; 
    }; 
} 
var instance = {}; 
Circle.call(instance, 5); 
instance.__proto__ = Circle.prototype; // we set the prototype of the new object to that of the constructor 
instance.area(); // ==> 78.5398 
var instance2 = new Circle(5); 
instance2.area() // ==> 78.5398 
instance instanceof Circle // ==> true // this is now true 
instance2 instanceof Circle // ==> true 

instance instanceof Circle ahora es cierto.

+2

+1, pásame, aunque probablemente deberías explicar por qué funciona, y la versión de OP no. – RMorrisey

+0

+1 de mí también, y el código de ejemplo que iba a publicar era idéntico :) (char para char). – pete

+0

@RMorrisey, Sí, es cierto. Estaba buscando esa charla sobre tecnología que acabo de publicar para verificar todo lo que voy a decir. Probablemente aún no le haga mucha justicia, pero lo publicaré en un segundo. – mowwwalker

0

gato no es un objeto. Es una función, y no creo que JavaScript lo soporte.

+4

Bueno, las funciones también son objetos, por lo que puede agregar propiedades a una función. – Guffa

+0

Guau, no sabía eso: D – PhpXp

2

Para que su código funcione como se desea que tendría que escribir:

function Cat(name) { 
    this.talk = function() { 
     alert(" say meeow!") 
    } 
}; 

var c = new Cat("felix"); 
c.talk() 

La función Cat es entonces una función constructor, y el objeto devuelto tiene una propiedad (talk), que es una función que Puedes llamar.

Su código original llegó a declarar una función talk mundial que no formaba parte de la función cat en absoluto, ya que faltaba la palabra clave var.

1

Eso es simplemente porque no lo es.

Ha creado una función y asignado a una variable en la función cat, pero esa variable no pertenece a la función. Como no declaras la variable en ninguna parte, implícitamente se vuelve global, por lo que en realidad está disponible fuera de la función, pero no de la manera en que intentas usarla.

Habría que añadir la función como una propiedad al objeto cat función, a fin de que usted pueda ser capaz de llamar de esa manera:

function cat(name) { 
    cat.talk = function() { 
    alert(" say meeow!") 
    } 
} 

cat("felix"); 
cat.talk() 

Sin embargo, es posible que se busca un objeto que tiene un método, en lugar de una función que tiene una propiedad que es un método:

function Cat(name) { 
    this.name = name; 
} 

Cat.prototype.talk = function() { 
    alert(this.name + " says meeow!"); 
} 

var felix = new Cat("Felix"); 
felix.talk(); 
+0

en realidad su función 'talk' es global, no local – Alnitak

+0

@Guffa, compruebe si está de acuerdo con mi edición. Por cierto, su muestra logra algo que la mayoría de la gente no espera: propiedad adicional en una función dada, a diferencia de la propiedad de un nuevo objeto creado por el constructor "cat". –

+0

Sí, tienes razón, es una variable global. Hice algunas ediciones extensas, pero incorporé tu punto. – Guffa