2011-02-05 16 views
5

Este es el código de trabajo:función Javascript tiene subfunciones/variables

var test = function() 
{ 
    console.log(test.data); 
}; 

test.data = 'hello'; 

test.set = function (data) 
{ 
    test.data = data; 
}; 

test.set('Test'); 
test(); 

Esto da salida a Test a mi consola de JavaScript. Ahora me preguntaba si había una forma de hacerlo usando algo como esto.

var test = { 
    this: function() 
    { 
     console.log(test.data); 
    }, 

    data: 'hello', 

    set: function (data) 
    { 
     test.data = data; 
    } 
}; 
+1

Las funciones son objetos, pero los objetos no son funciones. Por supuesto, puede almacenar funciones como propiedades de objeto pero no puede hacer que un objeto simple sea "invocable". ¿O qué es lo que realmente quieres lograr? ¿Cuál debería ser la ventaja de su segundo enfoque? –

+0

Quiero llamar a la función test.this() usando simplemente test() – Ragnis

+0

@Felix Creo que te estás perdiendo el punto, creo que está tratando de encapsular toda la información, y simplemente tener un enfoque más ordenado/más organizado. – xil3

Respuesta

5

Como he escrito en mi comentario, no puede hacer un objeto "invocable". Sin embargo, puede automatizar el proceso de su primer ejemplo:

function extend(func, props) { 
    for(var prop in props) { 
     if(props.hasOwnProperty(prop)) { 
      func[prop] = props[prop]; 
     } 
    } 
    return func; 
} 

y luego llamarlo con:

var test = extend(function(){ 
    console.log(test.data); 
}, 
{ 
    data: 'hello',  
    set: function (data) { 
     this.data = data; // note that I changed it to `this.data` 
    } 
}); 

DEMO


Dicho esto, creo que no se debe utilizar funciones como ese. Será más fácil de entender si solo tiene un objeto "normal" y llama a cada método con obj.method() en lugar de tener obj().

Al menos tiene que documentar esto con mucho cuidado.

+0

¿Dónde está la llamada 'hasOwnProperty'? ;) –

+0

@Ivo Wetzel: Bueno, supuse que uno pasaría solo objetos planos de todos modos ... pero sí ... la extensión de 'Object.prototype' ... bla bla ... (Espero que algún día ellos construyan el prototipos ** no ** ampliable!) ... corregido :) –

+0

Eso sería una gran cosa, pero dudo que alguna vez lo hagan: / –

0

Puede almacenar cualquier función en las propiedades de su objeto. Y puede invocarlos:

let f = { fun1: function() 
       { 
        return 1; 
       } 
     }; 
f.fun1(); 

va a funcionar perfectamente. No estoy seguro si puede usar 'esto' como nombre de propiedad ya que es una palabra clave. Probablemente no haya problema con eso, pero podría ser engañoso.

+0

En realidad, el segundo ejemplo fue más como un pseudo código. – Ragnis

2

¿Qué hay de hacer algo como esto:

function Test() { 
    this.data = 'hello'; 
    this.set = function (data) 
    { 
     test.data = data; 
    } 
    this.log = function() 
    { 
     console.log(test.data); 
    } 
} 

var test = new Test(); 
test.set('Test'); 
test.log(); 

Esto tiene la ventaja de que puede crear nuevas instancias fácilmente.


Si lo que desea es un hecho aislado, diría su propia sugerencia es casi lo que quiere:

var test = { 
    log: function() 
    { 
     console.log(test.data); 
    }, 

    data: 'hello', 

    set: function (data) 
    { 
     test.data = data; 
    } 
}; 

test.set('Test'); 
test.log(); 

Pero tal vez su pregunta fue cómo evitar la parte ".log"?

+0

Sí, quiero evitar esa parte ".log". – Ragnis

+0

¿Desea que el registro esté esencialmente en un constructor? – xil3