2017-06-07 1 views
2

J'ai le code vu en utilisant des classes Javascript utiliser le formulaire ci-dessous (exemple est React):Javascript méthodes de classe par rapport aux propriétés

class UserProfile extends Component { 
    state = { 
    open: false 
    } 

    handleOpen =() => { 
    this.setState({ open: true }) 
    } 
} 

Pourquoi handleOpen mis en œuvre comme une propriété qui est définie sur une fonction au lieu de quelque chose comme :

class UserProfile extends Component { 
    state = { 
    open: false 
    } 

    handleOpen() { 
    this.setState({ open: true }) 
    } 
} 

Merci d'avance!

+2

Veuillez noter que 'foo = ...' est une fonction * expérimentale *. Il ne fait pas encore partie des spécifications, certainement pas ES6. –

+0

@FelixKling, de quelle partie parlez-vous? – Chris

+0

@Chris: la syntaxe 'name = value' dans le corps de la classe à côté des définitions de méthodes (' foo() {} '). C'est actuellement une proposition et pas officiellement une partie de la langue. Voir https://tc39.github.io/proposal-class-public-fields/. –

Répondre

3

C'est aussi une fonction, mais elle s'appelle une fonction de flèche et fonctionne un peu différemment de l'implémentation "traditionnelle". Il a été introduit avec ECMAScript 6.

Voici ce que l'MDN docs dit:

Une expression de la fonction de flèche a une syntaxe plus courte qu'une function expression et ne lie pas son propre this, arguments, super ou new.target. Ces expressions de fonction sont mieux adaptées aux fonctions non-méthodes, et elles ne peuvent pas être utilisées en tant que constructeurs.


L'un des principaux avantages est que vous auriez pas besoin de lier this à cette fonction, car les fonctions de direction ne disposent pas de leur propre objet this:

Jusqu'à fonctions de direction, tous les nouvelle fonction définie sa propre valeur

Ceci garantit la sécurité de la portée; il est impossible d'utiliser le this incorrect par accident. Il est sans doute aussi légèrement plus lisible. Un inconvénient cependant serait que les fonctions de flèche sont anonymes, ce qui signifie qu'il serait plus difficile de faire une trace de pile lorsque vous obtenez une erreur dans votre code.

+2

Une autre différence est que la syntaxe de l'instance de classe (affectation de la fonction flèche) crée une nouvelle fonction pour chaque instance du composant. Avec la syntaxe de la méthode de classe, il existe une seule fonction que toutes les instances référencent et pour laquelle elles définissent le contexte approprié avant d'appeler (comme une chaîne prototype). Si vous utilisiez la syntaxe de l'instance de classe là où elle n'est pas nécessaire, vous créez des fonctions inutiles, et potentiellement beaucoup d'entre elles, lors de l'exécution. –

+1

@Chris dont Ross parle fait une différence beaucoup plus grande que si la fonction est une fonction de flèche ou non - 'handleOpen =() => ...' assignera une * copie * de cette fonction pour chaque instance de classe. 'handleOpen() {...}' l'assignera * une fois * sur 'UserProfile.prototype'. En général, la méthode 'prototype' devrait être préférée car elle ne dupliquera pas les affectations de fonctions. – naomik

1

Il s'agit du contexte de this à l'intérieur de votre méthode. Si vous souhaitez l'implémenter comme votre deuxième exemple, this ne référencera pas l'instance du composant, en utilisant la fonction de flèche comme dans votre premier exemple this fait référence à l'instance du composant. (En raison de ne pas utiliser React.createClass).

Pour votre deuxième exemple, vous devez faire this.handleOpen = this.handleOpen.bind(this) dans votre constructeur.

EDIT: Pour plus de détails sur arrow functions voir la réponse de Chris.

+0

Merci, c'est logique! – rhlsthrm