1
votes

Est-il possible que FORMAT ignore les directives de format non définies?

Je me demande s'il est possible de dire à FORMAT d'ignorer les directives de format non définies. J'ai regardé les pages FORMAT dans le CLHS mais je ne vois rien.

Ce que j'essaie de faire, c'est que FORMAT ignore ~ m dans une chaîne de format et affiche simplement ~ m au lieu d'essayer de le remplacer par quelque chose. Mon plan est qu'à ce stade, j'appellerai une autre fonction qui sait quoi faire avec ~ m .

Je suppose qu'une question connexe est alors, y a-t-il un moyen de définir une fonction pour gérer une directive de format qui n'est pas définie autrement?

En prévision de quelques questions. (1) Je suppose qu'une solution de contournement serait de remplacer un espace réservé pour ~ m , puis de le remplacer par la suite et de continuer. Je suppose que je le ferai si tout le reste échoue. (2) Je suppose qu'une autre stratégie générale serait d'appeler d'abord l'autre fonction, de gérer ~ m , puis d'appeler FORMAT sur le résultat. Malheureusement, cette autre fonction reconnaît certaines des mêmes directives, et barfs sur d'autres; il ne reconnaît pas que ~ m et ignore tout le reste.


2 commentaires

Pourriez-vous utiliser "~~ m" dans la chaîne de format pour générer "~ m" dans la sortie qui est ensuite transmise à l'autre fonction de traitement de chaîne?


Merci pour votre réponse. C'est une bonne idée, je suppose que cela fonctionnerait, même si j'espérais éviter de modifier la chaîne de contrôle.


3 Réponses :


3
votes

Vous pouvez définir votre propre directive de format avec ~ / nom /, où nom est le nom de la fonction appelée. Dans votre cas, vous auriez:

(format t "~/m/" 1)

(defun m (stream n colon-mod at-mod) 
   (format stream "~a" n)) ; or do something else with n

Vous devez toujours changer la chaîne de contrôle, mais vous pouvez ajouter une étape de prétraitement où "~ m" est remplacé par "~ / m /".


1 commentaires

La question de l'OA n'est pas très compréhensible. Vous n'avez pas besoin de ~ m car vous êtes déjà en train de définir la fonction qui fait qc à la place de ~ m avec n. mais merci, je ne savais pas que l'on pouvait définir ses propres directives de format.



1
votes

Je ne pense pas qu'il existe un moyen de le faire de manière portable (les implémentations peuvent vous permettre de faire toutes sortes de magie). J'écrirais une paire de fonctions quote-weird-tildes et dequote-weird-tildes , puis j'écrirais du code comme:

(defun format/qw (control &rest args)
  (declare (dynamic-extent args)
           (type string control))       ;can't be a function
  (dequote-weird-tildes
   (apply #'format nil (quote-weird-tildes control) args)))

Vous avez maintenant une fonction qui ressemble à (format nil ...) et qui n'est pas plus difficile à utiliser que cela. Pour plus de valeur, les fonctions de citation et de déquotation ne doivent pas utiliser de chaîne si elles ne sont pas obligées de le faire.


0 commentaires

1
votes

Depuis http://www.lispworks.com/documentation/ lw50 / CLHS / Body / 22_c.htm

L'argument de chaîne de contrôle pour formater est en fait un contrôle de format. Autrement dit, il peut s'agir d'une chaîne de format ou d'une fonction, par exemple un fonction renvoyée par la macro du formateur.

Vous pouvez donc faire:

~m1
NIL

Maintenant:

(format t (frmt "~m~A") 1)

sorties:

(defmacro frmt (control-string)
  (let ((str (cl-ppcre:regex-replace-all "~m" control-string "~~m"))) 
    `(formatter ,str)))

De cette façon, vous n'avez pas à modifier directement la chaîne de contrôle. Vous devez modifier l'appel au format pour inclure frmt.


0 commentaires