Système de passage d'arguments au compilateur/interpreteur :
{--encoding "UTF-8"}
{--clef valeur}
Changement du caractère d'indentation des blocs :
{--indent " "}
Arborescence des classes : étant donné que les classes font toutes parties de Main (par héritage, le "package" ou "namespace" correspondant à une classe donnée peut a fortiori être représenté par le chainage des classes dont elle hérite.
{-p "Racine.Sousracine.Blah.Parent"}
Comment implémenter le système d'entrée/sortie des paramètres de fonctions ?
Facilement représentable (avec des + ou des - ou des +-)
Execution différée :
: ins = \(
... instructions...
)
$(ins) {execution}
Forme étendue :
? condition
...
[[~ conditionsinon
...]
~ sinon
...]
;
Forme compacte :
? condition : si oui ~ si non
Condition sous la forme :
test1 & test2 ... | testN
Test sous la forme :
fonction("toto") & CONSTANTE & i = 0 | j >= 1
Pour-jusqu'à-faire :
@ conditioncontinuite [, instruction]*
...
;
Tantque-faire :
@ conditioncontinuite >
...
;
Repeter-tantque :
@ conditioncontinuite <
...
;
Pour-chaque :
@ liste : element
...
;
Boucle infinie :
@
...
;
Labels :
@[LABEL]
...
> [LABEL] ; {continue}
; [LABEL] > {break}
;
Le concept de la fonction comme on se l'imagine en tant que programmeur n'est pas implémenté dans Jix. En fait, toute fonction Jix se présente sous la forme d'une méthode qui est implicitement rattachée à l'objet initial Main.
On retrouvera donc la même synthaxe entre l'invocation de fonction et celle de méthode de classe :
fonction([parametres...])
Invocations chainées :
fonction([parametres...]), fonction2([parametre...]), fonctionN...
Pré-invocation de fonction :
\ fonction([parametre*])
Cela revient à ajouter l'opérateur "\" les paramètres sont transmis, mais l'invocation proprement dite est remise à un appel ultérieur de la fonction, cette fois ci avec l'opérateur "$"}
$(\ fonction([parametres...]))
Appel de constructeur :
Objet [parametre*] : instance = Objet([parametre*])
Appel de méthode :
instance.methode([parametre*]) Objet.methode([parametre*])
Remarques :
: [Parent.]Objet [Interface1 [Interface2...]] [--singleton] (
{déclaration d'une variable}
: [+|~|-][*]variable [= valeur]
{déclaration d'un constructeur}
: > [parametre*]
..([parametre*]) {sert à appeler le constructeur Parent, ".." == super}
;
{constructeur avec affectation implicite des variables}
: > variable
{variable étant déclarée en haut de la classe, nommer le paramètre à
{l'identique revient à demander l'affectation automatique
{explicitement : .variable = variable}
{destructeur}
: <
...
;
{déclaration d'une méthode d'instance}
: methode > [parametre*]
...
{retourne la valeur de paramètre}
< paramètre
;
{méthode appelée lors d'un print}
: '!' >
< "objet to string"
;
{redéfinir les opérateurs pour la somme (ou autre) de deux instances de
{type "Objet", doit impérativement retourner un objet de type identique}
: '[+|-|*|/|>|<|++|--|+=|-=|/=|*=|>=|<=]' > left right
left.methode( right.variable )
< left
;
{modificateur d'une variable d'instance de nom "var", instance.var = "blah" affectera "blah" à var}
: var >
) [Objet] {on peut mettre un label pour s'y retrouver}
Un bloc est un mécanisme particulier permettant d'encadrer l'execution d'une suite d'instructions par l'appel de deux fonctions, une en debut et une en fin de ladite suite.
Des variables peuvent être transmises à l'une ou l'autre de ces fonctions, il suffit de les nommer à l'identique dans le bloc, et dans les fonctions encadrantes :
: ClasseVerrou (
: fermer (verouiller deverouiller) > var1 var2
: verouiller > var1
...
[< true|false]
;
: deverouiller > var1 var2
...
[< true|false]
;
)
: verrou = ClasseVerrou()
verrou.fermer("blah" 0) (
... instructions ...
)
Cheminement de l'execution :
Les crochets sont échappés car ils doivent être explicitement écrits lors de la déclaration de l'interface, et ce afin de distinguer classe et interface
: \[Interface\] [Parent*] (
: methode > [parametre*]
...
)
Une fonction est en fait une méthode rattachée implicitement à l'objet Main.
: fonction > [parametre*]
...
;
Un groupe permet de retrouver une liste de méthodes sous un même drapeau :
: Classe (
# groupe (
: methode1 > [parametre*]
...
: methode2 > [parametre*]
...
)
: groupe.methode3 > [parametre*]
...
)
: objet = Classe()
objet.groupe.methode3()
Une variable peut être déclarée, puis affectée, ou les deux dans le même temps :
: variable {dans ce cas, la variable est de type Obj jusqu'à son affectation}
: variable = entier/booléen
: variable = "chaine"
: variable = Objet(...)
: variable = \(instruction*|invocation*) ou ?(condition)
Il est également possible d'écrire des affectations chainées, ou des déclarations chainées, ou les deux dans le même temps :
: var1, var2, var3 = valeur {trois instances sont créées}
: var4 = var1 += var2, var1 {var1 sera modifiée et var4 contiendra la valeur modifiée}
: var5, var6 = 1, 2 {var5 contiendra 1 et var6 contiendra 2}
Le langage ne contient pas de tableaux, juste des listes et des tables de hachage. Pour ce qui est des listes, le premier indice est 1, les autres suivent. En cas de modification, les indices sont mis à jour. Exemple : si un élément est supprimé, les indices suivant l'élément sont décalés vers la gauche. La synthaxe est la suivante :
: list = # : list = #(elem1 elem2 ... elemN) list += elemX list -= 1 : hash = Hsh() : hash = Hsh(key1 elem1 key2 elem2 ... elemN) hash += #(keyY elemY) hash -= key2
Les fichiers "*.i" = interfaces & "*.x" = classes :
{-i "librairie.x"}
{-i "librairie.i"}
"-" et "+" correspondent respectivement au flux d'erreur et à la sortie standard
si aucun flux n'est stipulé, "+" est par l'opérateur par défaut
! [flux] instruction ! [+|-] instruction
Le typage fort pose certaines contrainte qu'il est nécessaire d'aborder :
Types primitifs :
Classes primitives :
Explicite :
: variable = Boo(0) {la valeur booléenne faux est affectée à la variable}
: variable = Num(true) {la valeur numérique 1. est affectée à la variable}
: variable = Chr(0) {le caractère de code ascii 0 est affecté à la variable}
Implicite :
: variable = 0
{sera en fait considéré comme l'écriture de :}
: variable = Num(0.)
: variable = 0
variable = true
{la variable contiendra la valeur 1. car lors de son initialisation, il a été determiné que son type serait numérique}
{lui affecter ensuite une valeur booléenne revient à écrire :}
variable = Num(true)
: variable = "blah"
{la variable contiendra une instance de #.Str contenant autant d'éléments qu'il n'y a de caractères :}
: variable = Str("blah")
© 2010 DijxDreaM - All Rights Reserved