[voikko] Common Lisp ja libvoikko

Teemu Likonen tlikonen at iki.fi
Sun Jul 3 23:07:02 EEST 2011


Harri Pitkänen kirjoitti 3.7.2011 klo 18.01:

> UTF8-muotoisten sanojen oikolukuun tarvitset funktioita voikkoInit,
> voikkoSpellCstr ja voikkoTerminate. Näiden dokumentaatio löytyy
> tiedostosta /usr/include/libvoikko/voikko.h.

Kiitoksia. Tein makron ja funktion, joilla oikolukua voi helposti
kokeilla.


    (with-voikko-handle istunto
      (print (voikko-spell istunto "äidillä"))
      (print (voikko-spell istunto "äitillä")))

    T
    NIL


Näyttää toimivan. Tuntemattomasta sanasta palautetaan NIL (epätosi) ja
tutusta T (tosi). Alla on kyseinen makro ja funktio. Niiden
virheenkäsittely ei ole mitenkään täydellistä, mutta täytynee hioa, jos
innostun rakentamaan perusteellisemman rajapinnan Common Lispille.
Tuskin sille käyttäjiä on, mutta tällaisen harrastelijaohjelmoijan ei
tarvitse välittää muusta kuin siitä, että itsellä on hauskaa. :-)


    (cffi:load-foreign-library '(:default "libvoikko"))

    (defmacro with-voikko-handle (var &body body)
      (let ((voikko-error (gensym "ERROR"))
            (handle (gensym "HANDLE")))
        `(cffi:with-foreign-object (,voikko-error :char)
           (let* ((,handle (cffi:foreign-funcall "voikkoInit"
                                                 :pointer ,voikko-error
                                                 :string "fi_FI" :int 0
                                                 :pointer))
                  (,var ,handle))
             (declare (ignorable ,var))
             (if (and (cffi:pointerp ,handle)
                      (not (cffi:null-pointer-p ,handle))
                      (zerop (cffi:mem-aref ,voikko-error :char)))
                 (unwind-protect (progn , at body)
                   (cffi:foreign-funcall "voikkoTerminate"
                                         :pointer ,handle
                                         :void))
                 (error "Jotain meni vikaan"))))))

    (defun voikko-spell (handle string)
      (let ((value (cffi:foreign-funcall "voikkoSpellCstr"
                                         :pointer handle
                                         :string string
                                         :int)))
        (ecase value
          (0 nil)
          (1 t)
          (2 (error "Voikko: internal error"))
          (3 (error "Voikko: charset conversion failed")))))



More information about the voikko mailing list