2010-04-06 6 views
14

Je me demande un bon moyen de suivre si je voudrais redéfinir les membres d'une classe définie précédente dans ipython. dire: J'ai défini une intro de classe comme ci-dessous, et plus tard je veux redéfinir une partie de la définition de la fonction _print_api. Tout moyen de le faire sans le retaper.Bonne façon d'éditer la classe précédente définie dans ipython

class intro(object): 
    def _print_api(self,obj): 
      def _print(key): 
        if key.startswith('_'): 
          return '' 
        value = getattr(obj,key) 
        if not hasattr(value,im_func): 
          doc = type(valuee).__name__ 
        else: 
          if value.__doc__ is None: 
            doc = 'no docstring' 
          else: 
            doc = value.__doc__ 
        return '  %s  :%s' %(key,doc) 
        res = [_print(element) for element in dir(obj)] 
        return '\n'.join([element for element in res if element != '']) 
    def __get__(self,instance,klass): 
      if instance is not None: 
        return self._print(instance) 
      else: 
        return self._print_api(klass) 

Répondre

0

Il n'y a pas vraiment de "bonne" façon de le faire. Le mieux que vous pouvez faire est quelque chose comme ceci:

# class defined as normally above, but now you want to change a funciton 
def new_print_api(self, obj): 
    # redefine the function (have to rewrite it) 
    ... 
# now set that function as the _print_api function in the intro class 
intro._print_api = new_print_api 

Cela fonctionne même si vous avez déjà des objets d'introduction définis (qui est, lorsque vous appelez introObject._print_api sur un objet qui a déjà été créé, il appellera la nouvelle fonction que vous définissez). Malheureusement, vous devez encore redéfinir la fonction, mais au moins vous n'avez pas besoin de réécrire toute la classe. En fonction de votre utilisation, la meilleure chose à faire est de l'avoir dans un module séparé. import la classe et, lorsque vous avez besoin de changer quelque chose, utilisez simplement la fonction reload(). Cependant, cela n'affectera pas les instances précédentes de la classe (cela peut être ou ne pas être ce que vous voulez).

0

Lorsque vous arrivez au point où vous avez autant de code, il est plus simple de le mettre dans un fichier et import ce module particulier. Ensuite, lorsque vous avez besoin de mettre à jour, vous pouvez modifier le fichier et relancer l'instruction import et vous obtiendrez le code mis à jour, bien que les objets précédemment définis n'obtiennent pas les mises à jour.

+2

Pour obtenir le code mis à jour, vous devez utiliser la fonction 'reload (modulename)' - l'exécution de 'import' n'aura aucun effet (je crois que la raison en est que si un gros programme importe la même chose dans plusieurs endroits possibles, il n'encourt pas une grosse pénalité de performance). –

5

Si vous utilisez les fonctions d'édition ipython%, vous pouvez utiliser quelque chose comme this

10

Utilisez la commande d'édition%, ou son alias% ed. En supposant que la classe intro existe déjà dans l'espace de noms ipython, en tapant %ed intro ouvrira un éditeur externe sur le code source de la classe. Lorsque vous enregistrez et quittez l'éditeur, le code sera exécuté par ipython, redéfinissant efficacement la classe. L'inconvénient de ceci est que toutes les instances qui existent déjà seront toujours liées à l'ancienne version de la classe - s'il s'agit d'un problème, vous devez recréer les objets ou réattribuer l'objet obj. classe attribut pour pointer vers la nouvelle version de la classe.

Vous pouvez également utiliser %ed sur des modules, des fichiers et des lignes d'entrée précédentes, par ex. %ed 5 10:13 16 va créer et éditer un fichier composé de lignes d'entrée ipython 5,10,11,12,13,16.

+0

Vraiment un bon conseil! Loving iPython plus un plus .. –

+5

Hmm, cela devrait-il fonctionner avec des classes/fonctions qui étaient * définies * dans ipython, ou seulement avec celles importées? Le cas "classes définies dans ipython" ne fonctionne pas pour moi, j'obtiens ATTENTION: Le fichier 'None' où '' a été défini ne peut être lu. ' – weronika

+0

Cest ce que je cherche aussi - un bon moyen d'éditer une classe qui a été définie dans ipython. – Zitrax