Les membres ayant 30 points peuvent parler sur les canaux annonces, projets et hs du chat.
La shoutbox n'est pas chargée par défaut pour des raisons de performances. Cliquez pour charger.

Forum Casio - Projets de programmation


Index du Forum » Projets de programmation » WIP: LizyLang, un petit interpréteur de lisp bientôt on-calc.
Mb88 Hors ligne Rédacteur Points: 1196 Défis: 3 Message

WIP: LizyLang, un petit interpréteur de lisp bientôt on-calc.

Posté le 12/10/2024 21:38

>> Dépot git: https://github.com/mibi88/tinylisp <<


Fin septembre j'ai commencé à coder un petit interprétateur de mon propre dialecte de lisp, avec les calculatrices en tête. Mais c'est un peu galère de coder un interprétateur directement pour la calculatrice (sans shell, valgrind, etc.) donc je l'ai codé pour PC déjà et je vais bientôt le porter vers les calculatrices.

Pour l'instant il reste beaucoup à ajouter (surtout des fonctions), je ne suis même pas sur qu'il soit Turing complete (faut vraiment que j'essaye de coder le jeu de la vie avec, qui est Turing complete).

Il y a quelque trucs qui peuvent un peu surprendre: toutes les fonctions où la valeur qu'elles retournent est passé en argument d'une autre fonction sont appelées avant cette fonction, donc il ne faut pas faire (if (< n 10) (loop (- n 1)) 0), ou loop est appelé avant if, mais (callif (< n 10) loop (- n 1)), où la fonction callif se chargera d'appeler la fonction si la condition est vraie.

Un petit exemple:

(fncdef factorial (params n))
    (* (callif (> n 1) factorial (- n 1)) n)
(defend)

(print (factorial 6))


Affiche 720.000000

J'ai mis plein de tests dans le dépôt .

Amusez-vous bien !


Fcalva Hors ligne Membre Points: 569 Défis: 9 Message

Citer : Posté le 12/10/2024 21:44 | #


Et pourquoi ne pas utiliser un dialecte déja existant comme Scheme ou clisp ? Même en ne visant qu'une compatibilité partielle
Sinon c'est très cool, j'ai hâte d'avoir un autre langage on calc que le basic crade ou le python
Pc master race - Apréciateur de Noctua moyen
Caltos : G35+EII, G90+E (briquée )
Mb88 Hors ligne Rédacteur Points: 1196 Défis: 3 Message

Citer : Posté le 12/10/2024 21:45 | #


Fcalva a écrit :
Et pourquoi ne pas utiliser un dialecte déja existant comme Scheme ou clisp ? Même en ne visant qu'une compatibilité partielle


Parce que là je peux appeler les fonctions dans l'ordre que je veux

Non mais sinon c'est plus fun comme ça.
Mb88 Hors ligne Rédacteur Points: 1196 Défis: 3 Message

Citer : Posté le 13/10/2024 14:44 | #


J'ai ajouté des fonctions pour gérer les listes (test items.lsp).

- (len l): retourne la longueur de la liste l.
- (get l i): retourne l'élément à l'index i (le premier index est 0) de la liste l.

J'ai aussi ajouté des fonctions strlen et strget qui permettent de faire les mêmes opérations sur des chaînes de caractères.
Mb88 Hors ligne Rédacteur Points: 1196 Défis: 3 Message

Citer : Posté le 13/10/2024 21:08 | # | Fichier joint


J'ai codé le jeu de la vie avec: https://github.com/mibi88/tinylisp/blob/master/test/gameoflife.lsp

À la fin il vous affiche le clown normalement



Par contre il est hyper lent (13 secondes pour avoir ce clown), et le code est crade parce qu'il y a des bugs dans l'interpréteur que j'ai dû contourner (faut que je les corrige).

Mais il est donc turing complete !
Mb88 Hors ligne Rédacteur Points: 1196 Défis: 3 Message

Citer : Posté le 15/10/2024 20:39 | #


L'interpréteur est très très lent actuellement, et j'aime pas trop ma bricole de callif. J'ai aussi du mal à retourner des valeurs. Je suis donc en train de le modifier grandement en générant un AST. J'arrive déjà à créer un arbre, auquel j'ajoute des nœuds et je passe d'un nœud à l'autre.

J'ai pas grand chose à montrer actuellement à part ça (en exécutant simple.lsp).

-> New node
<- Go to the root node
-> New node
-> New node
<- Go to the parent node
<- Go to the root node
-> New node
-> New node
-> New node
<- Go to the parent node
<- Go to the parent node
<- Go to the root node
-> New node
-> New node
<- Go to the parent node
<- Go to the root node


EDIT:

Il me permettra de n'appeler les fonctions que si besoin.
Kikoodx Hors ligne Ancien labélisateur Points: 3032 Défis: 11 Message

Citer : Posté le 15/10/2024 21:13 | #


cool cool ! bon courage avec ce projet, et oublie pas getkey ;)

c'est sûrement connu ici avec Lephé qui rode, mais j'avais fait une bonne partie de make a lisp il y a de ça quelques mois, c'est assez dru à lire mais assez complet et leur structure est décente

nb: je link pas forcèment pour ton projet en cours, mais si t'aimes tout ce qui est lié aux langages de prog c'est assez intéressant à faire sur une semaine ou deux
ouais ouais
Lephenixnoir En ligne Administrateur Points: 24531 Défis: 170 Message

Citer : Posté le 15/10/2024 21:18 | #


Fact : je ne connaissais pas make a lisp
Mon graphe (11 Avril): ((Rogue Life || HH2) ; PythonExtra ; serial gint ; Boson X ; passe gint 3 ; ...) || (shoutbox v5 ; v5)
Mb88 Hors ligne Rédacteur Points: 1196 Défis: 3 Message

Citer : Posté le 15/10/2024 21:25 | #


Pareil, je ne connaissais pas. Impressionnant le nombre d'implémentations. Mais bon, je vais pas trop regarder comment ils ont fait pour faire mon interpréteur entièrement à ma façon (c'est plus intéressant que de recopier le truc de quelqu'un d'autre).
Mb88 Hors ligne Rédacteur Points: 1196 Défis: 3 Message

Citer : Posté le 16/10/2024 20:02 | #


Voilà, j'ai fini de générer l'arbre.

-> New node
|_ Function name
|_ String argument
<- Go to the root node
-> New node
|_ Function name
|_ Argument
-> New node
|_ Function name
|_ String argument
<- Go to the parent node
<- Go to the root node
-> New node
|_ Function name
-> New node
|_ Function name
-> New node
|_ Function name
|_ String argument
|_ Argument
<- Go to the parent node
|_ String argument
<- Go to the parent node
<- Go to the root node
-> New node
|_ Function name
-> New node
|_ Function name
|_ Argument
|_ Argument
<- Go to the parent node
<- Go to the root node


Je vais pouvoir commencer à utiliser mon arbre !
Mb88 Hors ligne Rédacteur Points: 1196 Défis: 3 Message

Citer : Posté le 16/10/2024 20:48 | #


J'ai poussé mon code de génération d'arbre, la dernière version sur master ne fonctionne donc pas (elle n'exécute pas les scripts, elle n'en fait que l'arbre, et j'avais la flemme de faire une autre branche), donc si vous souhaitez essayer TinyLisp, téléchargez le code source de la release v.0.1 (https://github.com/mibi88/tinylisp/releases/tag/v.0.1).
Mb88 Hors ligne Rédacteur Points: 1196 Défis: 3 Message

Citer : Posté le 19/10/2024 14:19 | #


Calling "comment"
Calling "strdef"
Calling "input"
Name > Mibi88
Calling "print"
Calling "+"
Calling "+"
Hello, Mibi88!
Calling "print"
Calling "+"
5.500000


Je peux de nouveau exécuter simple.lsp !

Mais maintenant TinyLisp fait de l'évaluation paresseuse !

EDIT :

Sans les logs pour le débogage :
Name > Mibi88
Hello, Mibi88!
5.500000

Lephenixnoir En ligne Administrateur Points: 24531 Défis: 170 Message

Citer : Posté le 19/10/2024 16:19 | #


Pour ton évaluation paresseuse (après brève échange sur #projets) t'es sûr que c'est pas du call-by-name ?
Mon graphe (11 Avril): ((Rogue Life || HH2) ; PythonExtra ; serial gint ; Boson X ; passe gint 3 ; ...) || (shoutbox v5 ; v5)
Mb88 Hors ligne Rédacteur Points: 1196 Défis: 3 Message
Lephenixnoir En ligne Administrateur Points: 24531 Défis: 170 Message

Citer : Posté le 19/10/2024 17:42 | #


Je te le fais en C parce que je sais pas vraiment écrire du Lisp

La stratégie d'évaluation classique des langages impératifs c'est tu calcules les arguments avant d'appeler :

void f(int x, int y) { int z = 4; printf("%d", x); printf("%d", x); printf("%d", z); }
f(printf("hello "), printf("y "));
// hello y 664

printf() renvoie le nombre de caractères affichés donc 6 pour "hello " et 2 pour "y ". Techniquement en C c'est pas spécifié dans quel ordre les arguments sont évalués mais on va dire de gauche à droite pour faire simple.

Si tu délaies juste l'évaluation de l'argument au moment où tu exécutes la fonction tu as l'impression de faire le bon truc, mais il y a deux problèmes. D'abord, tu peux évaluer l'argument plusieurs fois :

void f(int x, int y) { int z = 4; printf("%d", x); printf("%d", x); printf("%d", z); }
f(printf("hello "), printf("y "));
// hello 6hello 64

Et ensuite (et surtout, pire !) l'argument est interprété dans le contexte de la fonction donc toutes les références aux variables sont en vadrouille :

void f(int x, int y) { int z = 4; printf("%d", x); printf("%d", x); printf("%d", z); }
f(z, printf("y "));
// 444

Là le z bind sur la variable locale de f, ce qui n'a aucun sens !! (enfin presque y'a des langages qui marchent comme ça mais uurrrh)

Pour faire du call-by-need (i.e. paresseux), il faut donc (1) que tu évalues les arguments dans l'environnement de l'appel et pas de l'utilisation de l'argument (ce qui est plutôt difficile et implique des clôtures ou un truc équivalent), et (2) que tu gardes le résultat de l'évaluation des arguments en cache.
Mon graphe (11 Avril): ((Rogue Life || HH2) ; PythonExtra ; serial gint ; Boson X ; passe gint 3 ; ...) || (shoutbox v5 ; v5)
Mb88 Hors ligne Rédacteur Points: 1196 Défis: 3 Message

Citer : Posté le 19/10/2024 18:45 | #


Je suis en train d'ajouter la définition de fonctions et oui, je commence a avoir à faire face à ces problèmes…

Mais bon, l'évaluation paresseuse est vraiment trop cool !
Lephenixnoir En ligne Administrateur Points: 24531 Défis: 170 Message

Citer : Posté le 19/10/2024 18:49 | #


Je joue un peu avec ça dans un langage fonctionnel lazy pour la définitions d'interfaces graphiques dans JustUI (par ici) et ça part vite en vrille avec des thunks dans tous les sens, surtout quand il y a des trucs récursifs. x)

AFAIK Lisp est habituellement strict, documente bien tout ce qui est lazy
Mon graphe (11 Avril): ((Rogue Life || HH2) ; PythonExtra ; serial gint ; Boson X ; passe gint 3 ; ...) || (shoutbox v5 ; v5)
Mb88 Hors ligne Rédacteur Points: 1196 Défis: 3 Message

Citer : Posté le 20/10/2024 13:48 | #


Mon dialecte de Lisp a un nouveau nom: LizyLang

https://github.com/mibi88/lizylang/blob/master/README.txt#L6-L18
Some time ago, I watched a video by Tantan (https://youtu.be/Qg8OGAfiG7M), where he ranked programming language names. I wanted to give my programming language a cool name, and after some thinking I came up with this name by trying to combine "lisp" and "lazy".

It is composed of "Li" for lisp, "zy" for lazy and "lang" because it is a programming language.

It should be pronounced [lizjˈleɪŋɡ]

The file extension is .lzy


(Oui j'ai un peu la flemme de réécrire le texte de mon readme)

J'ai encore quelque changements à faire dans le code, mais sinon tout les tests ont adopté la nouvelle extension, et j'ai déjà changé le nom du dépôt. J'espère que ce nom vous plaît aussi !

LienAjouter une imageAjouter une vidéoAjouter un lien vers un profilAjouter du codeCiterAjouter un spoiler(texte affichable/masquable par un clic)Ajouter une barre de progressionItaliqueGrasSoulignéAfficher du texte barréCentréJustifiéPlus petitPlus grandPlus de smileys !
Cliquez pour épingler Cliquez pour détacher Cliquez pour fermer
Alignement de l'image: Redimensionnement de l'image (en pixel):
Afficher la liste des membres
:bow: :cool: :good: :love: ^^
:omg: :fusil: :aie: :argh: :mdr:
:boulet2: :thx: :champ: :whistle: :bounce:
valider
 :)  ;)  :D  :p
 :lol:  8)  :(  :@
 0_0  :oops:  :grr:  :E
 :O  :sry:  :mmm:  :waza:
 :'(  :here:  ^^  >:)

Σ π θ ± α β γ δ Δ σ λ
Veuillez donner la réponse en chiffre
Vous devez activer le Javascript dans votre navigateur pour pouvoir valider ce formulaire.

Si vous n'avez pas volontairement désactivé cette fonctionnalité de votre navigateur, il s'agit probablement d'un bug : contactez l'équipe de Planète Casio.

Planète Casio v4.3 © créé par Neuronix et Muelsaco 2004 - 2024 | Il y a 92 connectés | Nous contacter | Qui sommes-nous ? | Licences et remerciements

Planète Casio est un site communautaire non affilié à Casio. Toute reproduction de Planète Casio, même partielle, est interdite.
Les programmes et autres publications présentes sur Planète Casio restent la propriété de leurs auteurs et peuvent être soumis à des licences ou copyrights.
CASIO est une marque déposée par CASIO Computer Co., Ltd