Version française
Home     About     Download     Resources     Contact us    
Browse thread
ocamlyacc and empty objects
[ Home ] [ Index: by date | by threads ]
[ Search: ]

[ Message by date: previous | next ] [ Message in thread: previous | next ] [ Thread: previous | next ]
Date: -- (:)
From: patrik osgnach <patrik.osgnach@g...>
Subject: ocamlyacc and empty objects
Hi, I'm doing some experiments with ocamlyacc and ocamlex. these are the
sources
lex.mll
------------------------
{
   open String
   open Par
   let rec string2list str = match str with
     | "" -> []
     | _ -> try (let pos = index str ',' in
      (sub str 0 pos)::(string2list (sub str (pos+1) ((length
str)-(pos+1)))))
      with Not_found -> str::[]
   ;;
}
let num = ['0'-'9'] | ['1'-'9']['0'-'9']+
let name = ['a'-'z']['a'-'z' 'A'-'W' 'Y'-'Z' '0'-'9']*
let sigtype = "active" | "passive" | "atomic"
let sigelem = sigtype ' ' name ':' num
let sigset = '[' sigelem (',' sigelem)* ']'
let Sig = "Signature " sigset ';'

rule token = parse
   | [' ' '\t'] { token lexbuf }
   | '\n' { NEWLINE }
   | Sig as snl { SIGNATURE (string2list(sub snl (index snl '['+1) (index
snl ']'- index snl '[' -1 ))) }
   | name as nm { NAME(nm) }
   | eof { NEWLINE }
------------------
par.mly
------------------
%{
   open Printf
   open Lexing
   open String
   type sigdata = string*string*int
module Signature =
struct
   type t = string * int
   let compare (sig1, n1) (sig2, n2) =
     if sig1 < sig2 then - 1
     else if sig1 > sig2 then 1
     else 0
end;;
module SignatureSet = Set.Make(Signature);;
class signatures = object (self)
   val mutable s = SignatureSet.empty
   method addsign sign n = s <- SignatureSet.add (sign, n) s
   method removesign sign = s <- SignatureSet.remove (sign, 0) s
   method arity (sign : string) = List.assoc sign (SignatureSet.elements s)
   method getsigns = SignatureSet.elements s
end;;

   let sign = new signatures;;
   let rec signaturedata data = match data with
     | [] -> []
     | head::tail -> (sub head 0 (index head ' '),sub head (index head '
' +1) (index head ':' - index head ' ' -1), int_of_string (sub head
(index head ':' +1) (length head - index head ':' -1)))::signaturedata tail
     ;;
   let rec makeSigSet data = match data with
     | [] -> ()
     | (t, n, a)::tail -> sign#addsign n a; makeSigSet tail
   ;;
%}
%token <string list> SIGNATURE
%token <string> NAME
%token NEWLINE
%start boh
%type <string> boh
%%
boh:
   SIGNATURE NEWLINE bg NEWLINE{ makeSigSet (signaturedata
$1);string_of_int (sign#arity "server") ^ $3}
;
bg:
   | NAME {(*string_of_int (sign#arity "server")*) "a" }
;
-------------------
there is also a simple main module which reads from a file and starts
the parser. this is the source file
-----------------
Signature [active server:2];
blablabla
-----------------
sing is a simple set of string*int pairs and it contains only the pair
("server", 2). my problem is: the first time I call getsigns method
(after boh:) I get a "2" (which is correct), second time (under bg:) I
get a Not_found exception. Do you know why?

thanks for help
patrik
(sorry for my bad english)