Modèle de syntaxe Vim pour mettre en surbrillance l'argument du mot clé python

17

J'ai du mal à apprendre les expressions rationnelles de vim (je ne connais pas très bien d'autre expression régulière), donc le problème principal est de définir une expression rationnelle qui correspondrait

some_function_call(simple_value, keyword=value)

dans cet exemple.

Il doit donc correspondre à un mot s'il se trouve à l'intérieur de parens et avoir un signe égal après.

Le problème suivant est de savoir comment définir des fichiers de syntaxe dans vim. J'apprécierais de l'aide pour cela, mais cela ne devrait pas être si difficile à apprendre, donc je peux probablement le faire moi-même.

EDIT basé sur la réponse que j'ai fournie mon propre script de syntaxe pour python. N'hésitez pas à l'essayer. entrez la description du lien ici

user1685095
la source
Il existe un problème ouvert sur Github pour la mise en surbrillance des mots clés à inclure dans le fichier de syntaxe Python le plus récent que je connaisse: github.com/hdima/python-syntax/issues/44 Vous voudrez peut-être y vérifier plus tard. Si vous comprenez comment le faire, veuillez en informer les personnes présentes (ou m'envoyer un message afin que je puisse créer une demande d'extraction) pour que cette fonctionnalité soit disponible pour tout le monde.
cbaumhardt
1
Ouais, c'est moi qui l'ai ouvert.
user1685095

Réponses:

12

Avec ces paramètres:

syn region FCall start='[[:alpha:]_]\i*\s*(' end=')' contains=FCall,FCallKeyword
syn match FCallKeyword /\i*\ze\s*=[^=]/ contained
hi FCallKeyword ctermfg=yellow

Je reçois:

entrez la description de l'image ici

Ici:

  1. Je définis une région de syntaxe dans laquelle les arguments de mots clés peuvent être trouvés, ce serait l'appel de fonction. L' containsoption me permet d'imbriquer les appels de fonction.
  2. Dans cette région, je fais correspondre n'importe quelle chaîne composée de caractères d'identification valides ( \i*) suivis =, mais pas ==, de sorte que les tests d'égalité ne correspondent pas.

En utilisant des régions, j'arrive à imbriquer les correspondances autant que je le souhaite, ce qui aurait été très compliqué (impossible?) Si j'avais opté pour une matchexpression régulière.

Je crois que les expressions régulières utilisées pour faire correspondre l'appel de fonction et le mot-clé peuvent être affinées, mais compte tenu de ce qui est valide dans Python 3 , ce n'est pas une tâche que je suis prêt à assumer.

En option, je pense que vous pouvez l'utiliser pour mettre en évidence les appels de fonction, en utilisant matchgroup:

syn region FCall matchgroup=FName start='[[:alpha:]_]\i*\s*(' end=')' contains=FCall,FCallKeyword
syn match FCallKeyword /\i*\ze\s*=[^=]/ contained
hi FCallKeyword ctermfg=yellow
hi FName ctermfg=blue

entrez la description de l'image ici

muru
la source
Je devrais probablement créer une autre question, mais avez-vous des idées sur la façon de mettre en évidence uniquement les fonctions intégrées?
user1685095
@ user1685095 Les fonctions intégrées sont répertoriées dans le pythonBuiltingroupe de syntaxe par défaut syntax/python.vim. Cependant, il ne fait pas de distinction entre les fonctions et les variables intégrées ( True, Falseet se Nonetrouvent également dans pythonBuiltin). Vous pourriez probablement copier les définitions pour votre usage.
muru
Eh bien, j'ai utilisé une syntaxe plus raffinée que vim par défaut comme hdima / python et vim-polyglot. Ils définissent tous des fonctions intégrées comme un mot-clé qui ont des conséquences importantes. Non seulement les fonctions intégrées sont mises en évidence, mais seules les variables portant le même nom et les fonctions des autres modules portant le même nom sont mises en évidence. Comme le query(...).***filter***()filtre est mis en évidence alors qu'il n'a rien à voir avec les fonctions de filtre intégrées.
user1685095
@ user1685095 la valeur par défaut en syntax.vimfait des mots clés. Voir github.com/vim/vim/blob/master/runtime/syntax/python.vim#L184
muru
1
@ user1685095 Odd. Je n'ai pas de syntax/python.vimfichiers supplémentaires (seulement la valeur par défaut, et je ne vois pas le comportement que vous faites: i.stack.imgur.com/LgF6F.png , et je suis d'accord avec la définition du mot clé - c'est la forme la plus proche, et je ne pensez pas que les mots-clés sont mis en correspondance dans des cas comme nonkeyword.keyword. En ce qui concerne les variables, notez que ces prédéfinis sont des variables, ce sont des variables contenant des objets fonction, et peuvent être assignées à tout comme les autres variables. Rien ne vous empêche de faire sorted = filteret d'utiliser ensuite sortedcomme filter.
muru
8

Voici où vous pouvez commencer:

/([^,]\+,\s\(\w\+\)=.*)

Décomposition:

/(       start matching a (
[^,]\+   match multiple characters that are not ,
,\s      match a , and a space
\(       start a matching group
\w\+     match word characters
\)       end the matching group
=.*)      match an = and anything until the closing )

Cela nécessite des améliorations mais vous donne un aperçu de la façon dont vous pouvez le faire.

nobe4
la source
6

En plus de la réponse @ Nobe4, vous pouvez effectuer les opérations suivantes:

  • Créer le fichier ~/.vim/after/syntax/python.vim
  • Mettez cette ligne dans le fichier:

    syntax match PythonArg /(.*\,\s*\zs\w\+\ze\s*=.*)/
    hi PythonArg guibg=blue
    
  • Adaptez le second avec vos valeurs préférées.

Cela créera un fichier de syntaxe qui ajoutera une correspondance de syntaxe pour vos arguments suivi d'un =et définira le style à utiliser. Ce sujet :h mysyntaxfile-adddevrait être intéressant pour vous.

J'ai également utilisé un regex différent de l'autre réponse, voici le détail (je ne sais pas lequel fonctionne mieux, vous devrez probablement essayer):

(      Begin the pattern with a bracket
.*,    Look for any number of any character before a ,
\s*    Zero or more white spaces after the ,
\zs    Start the matching group (what will be highlighted)
\w\+   Match one or more word characters
\ze    End the matching group
\s*    Zero or more white spaces between your argument and the = sign
=      A literal = sign after your argument
.*)    Any number of any characters between your = sign and the closing bracket
statox
la source
Merci pour ton aide. Je ne savais pas que je pouvais ajouter ma syntaxe personnalisée sans modifier les règles existantes. Votre modèle ne correspond pas à l'argument mot-clé s'il s'agit d'un premier argument dans la fonction. Je vais essayer de résoudre ce problème moi-même (j'apprends des expressions rationnelles en ce moment pour le faire). Dès que j'apprendrai à le faire, je posterai un commentaire.
user1685095
J'essaie cette expression rationnelle via la recherche vim et je pense qu'elle ne correspond qu'à un seul mot clé dans l'appel de fonction. J'en ai besoin pour correspondre à tous ''
user1685095
@ user1685095: Oui, vous avez raison, mon modèle n'est pas bon. Je vais essayer de l'améliorer et de modifier ma réponse.
statox
3

J'ai trouvé que la réponse de @ Wolfie capture le déballage d'un tuple en tant que mot clé et qu'il a également eu du mal à capturer les arguments de mots clés interrompus.

Inspiré par son expression régulière, j'ai trouvé ce qui suit pour mettre dans mon python.vimfichier de syntaxe. (Gardez à l'esprit que j'utilise à l'origine le python.vimfichier de syntaxe de sheerun / vim-polyglot )

syn match pythonFunctionKeyword "\v\s{-}\zs\w+\ze\=(\=)@!(\_s)@!" display
syn cluster pythonExpression add=pythonFunctionKeyword
syn region pythonFunctionKwargs start=+(+ end=+)+ contains=@pythonExpression

Et la ventilation des regex est très similaire à la réponse de @ Wolfie :

\v      set to very magic mode
\s{-}   capture whitespace, nongreedy
\zs     start of the match (what to actually highlight)
\w+     one or more alphanumeric character, underscore included
\ze     stop matching; anything after this is delimiting only
\=      one single equal sign
(\=)@!  ...not followed by another equal sign
(\_s)@! ...not followed by any whitespace or newline character

Notez que ce ne sera pas la couleur d' un mot - clef argument écrit: key = value. Ce que je considère comme une bonne chose, car cela va à l'encontre de la recommandation officielle des espaces blancs PEP-8 pour les arguments de mots clés .

Ludo
la source
2

La réponse acceptée au moment de l' écriture a cassé la mise en évidence des chaînes dans les listes d'arguments de fonction pour moi (par quelle alchimie je ne sais pas), alors voici une version, je l'espère, plus sûre, basée sur celle de Statox .

syntax match PythonArg "\v[\(\,]\s{-}\zs\w+\ze\s{-}\=(\=)@!"
hi PythonArg ctermfg = 214 guifg = #ffaf00

ctermfgest pour le terminal de console, guifgest pour gui. Bien sûr, vous êtes libre de changer les couleurs selon vos envies. Voici une liste pratique .

Comme toujours, tu ferais mieux de mettre ça à l'intérieur ~/.vim/after/syntax/python.vim

Pour une ventilation regex, vous allez ici:

\v      set to very magic mode
[\(\,]  capture either a ( or a ,
\s{-}   capture whitespace, nongreedy
\zs     start of the match (what to actually highlight)
\w+     one or more alphanumeric character, underscore included
\ze     stop matching; anything after this is delimiting only
\s{-}   once again, capture whitespace.
\=      one single equal sign
(\=)@!  ...not followed by another equal sign

La vérification finale arrête la mise en évidence des couleurs conditionnelles. Vous pouvez le supprimer si vous le souhaitez.

Wolfie
la source
Désolé, vous êtes en retard. J'ai moi-même un fichier de syntaxe.
user1685095
C'est très bien; si quelqu'un d'autre rencontre le même problème que moi, il peut, je l'espère, jeter un œil ici.
Wolfie