Update of /cvsroot/audacity/audacity-src/nyquist
In directory 23jxhf1.ch3.sourceforge.com:/tmp/cvs-serv14284

Modified Files:
        dspprims.lsp fileio.lsp nyinit.lsp nyquist.lsp sal-parse.lsp 
        sal.lsp xm.lsp 
Log Message:
Updating to Nyquist v3.03.


Index: sal-parse.lsp
===================================================================
RCS file: /cvsroot/audacity/audacity-src/nyquist/sal-parse.lsp,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -d -r1.1 -r1.2
--- sal-parse.lsp       30 Jan 2009 00:54:45 -0000      1.1
+++ sal-parse.lsp       5 Mar 2009 17:42:25 -0000       1.2
@@ -393,7 +393,7 @@
   (setf delimiter-stack nil)
   (setf delimiter-mismatch nil))
 (defun delimiter-match (tok what)
-  (cond ((eql (first delimiter-stack) what)
+  (cond ((eql (token-string (first delimiter-stack)) what)
          (pop delimiter-stack))
         ((null delimiter-mismatch)
          ;(display "delimiter-mismatch" tok)
@@ -401,7 +401,7 @@
 (defun delimiter-check (tok)
   (let ((c (token-string tok)))
     (cond ((member c '(#\( #\{ #\[))
-           (push c delimiter-stack))
+           (push tok delimiter-stack))
           ((eql c +rbrace+)
            (delimiter-match tok +lbrace+))
           ((eql c +rparen+)
@@ -1423,18 +1423,20 @@
     
 ;; PARSE-ASSIGN -- based on parse-bind, but with different operators
 ;;
+;; allows arbitrary term on left because it could be an array
+;; reference. After parsing, we can check that the target of the
+;; assignment is either an identifier or an (aref ...)
+;;
 (defun parse-assign ()
-  (let (id op val)
-    (if (token-is :id)
-        (setf id (token-lisp (parse-token)))
-        (errexit "expected a variable name"))
-    ;; if it's id[expr], replace id with (aref id expr)
-    (setf id (maybe-aref id))
+  (let ((lhs (parse-term) op val))
     (cond ((token-is '(:= :-= :+= :*= :/= :&= :@= :^= :<= :>=))
            (setf op (parse-token))
            (setf op (if (eq (token-type op) ':=) '= (token-lisp op)))
            (setf val (parse-sexpr))))
-    (list id op val)))
+    (cond ((and (consp lhs) (eq (car lhs) 'aref))) ;; aref good
+          ((symbolp lhs)) ;; id good
+          (t (errexit "expected a variable name or array reference")))
+    (list lhs op val)))
 
 
 (defun maybe-parse-loop ()
@@ -1602,6 +1604,8 @@
     (list binding term-test)))
 
     
+;; parse-sexpr works by building a list: (term op term op term ...)
+;; later, the list is parsed again using operator precedence rules
 (defun parse-sexpr (&optional loc)
   (let (term rslt)
     (push (parse-term) rslt)
@@ -1622,7 +1626,17 @@
   (third (assoc op +operators+)))
 
 
-(defun parse-term ()
+;; a term is <unary-op> <term>, or
+;;           ( <sexpr> ), or
+;;           ? ( <sexpr> , <sexpr> , <sexpr> ), or
+;;           <id>, or
+;;           <id> ( <args> ), or
+;;           <term> [ <sexpr> ]
+;; Since any term can be followed by indexing, handle everything
+;; but the indexing here in parse-term-1, then write parse-term
+;; to do term-1 followed by indexing operations
+;;
+(defun parse-term-1 ()
   (let (sexpr id)
     (cond ((token-is '(:- :!))
            (list (token-lisp (parse-token)) (parse-term)))
@@ -1642,9 +1656,9 @@
            (token-lisp (parse-token)))
           ((token-is :id) ;; aref or funcall
            (setf id (token-lisp (parse-token)))
-           (cond ((token-is :lb)
-                  (setf id (maybe-aref id)))
-                 ((token-is :lp)
+           ;; array indexing was here, but that only allows [x] after
+           ;; identifiers. Move this to expression parsing.
+           (cond ((token-is :lp)
                   (parse-token)
                   (setf sexpr (cons id (parse-pargs t)))
                   (if (token-is :rp)
@@ -1656,15 +1670,16 @@
            (errexit "expression not found")))))
 
 
-(defun maybe-aref (id)
-  (cond ((token-is :lb)
-         (parse-token)
-         (setf id
-               (list 'aref id (parse-sexpr)))
-         (if (token-is :rb)
-             (parse-token)
-             (errexit "right bracket not found"))))
-  id)
+(defun parse-term ()
+  (let ((term (parse-term-1)))
+    ; (display "parse-term" term (token-is :lb))
+    (while (token-is :lb)
+      (parse-token)
+      (setf term (list 'aref term (parse-sexpr)))
+      (if (token-is :rb)
+          (parse-token)
+          (errexit "right bracket not found")))
+    term))
 
 
 (defun parse-ifexpr ()

Index: fileio.lsp
===================================================================
RCS file: /cvsroot/audacity/audacity-src/nyquist/fileio.lsp,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -d -r1.1 -r1.2
--- fileio.lsp  30 Jan 2009 00:54:45 -0000      1.1
+++ fileio.lsp  5 Mar 2009 17:42:25 -0000       1.2
@@ -20,7 +20,7 @@
                    (setdir "e:\\tmp\\")
                    (setdir "e:\\temp\\")
                   (get-temp-path)))
-         (format t "Set *default-sf-dir* to ~A in fileio.lsp~%" 
+         (format t "Set *default-sf-dir* to \"~A\" in fileio.lsp~%" 
                 *default-sf-dir*)
         (setdir current))))
 
@@ -143,6 +143,8 @@
 ;;   the *autonorm-target*
 ;;
 (defun autonorm-update (peak)
+  (cond ((> peak 1.0)
+         (format t "*** CLIPPING DETECTED! ***~%")))
   (cond ((and *autonormflag* (> peak 0.0))
            (setf *autonorm-previous-peak* (/ peak *autonorm*))
          (setf *autonorm* (/ *autonorm-target* *autonorm-previous-peak*))
@@ -151,10 +153,12 @@
          (format t (if (eq *autonorm-type* 'PREVIOUS)
                        "     new normalization factor is ~A~%"
                        "     suggested normalization factor is ~A~%")
-                 *autonorm*)
-         *autonorm-previous-peak*
-        )
-        (t peak)
+                 *autonorm*))
+        (t
+         (format t "Peak was ~A,~%" peak)
+         (format t "     suggested normalization factor is ~A~%"
+                   (/ *autonorm-target* peak)))
+   peak
   ))
 
 ;; s-read -- reads a file

Index: xm.lsp
===================================================================
RCS file: /cvsroot/audacity/audacity-src/nyquist/xm.lsp,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -d -r1.1 -r1.2
--- xm.lsp      30 Jan 2009 00:54:46 -0000      1.1
+++ xm.lsp      5 Mar 2009 17:42:25 -0000       1.2
@@ -1046,6 +1046,7 @@
         (dotimes (i order)
           (push (nth i rule) pattern))
         (push (cons (reverse pattern) entry) rules)))
+    (setf rules (reverse rules)) ;; keep rules in original order
     (setf *rslt* nil) ;; in case produces is nil
     (cond ((and produces (not (is-produces-homogeneous produces)))
            (setf produces (make-produces-homogeneous produces))))
@@ -1096,6 +1097,7 @@
 
 (send markov-class :answer :find-rule '()
   '((let (rslt)
+      ;(display "find-rule" rules)
       (dolist (rule rules)
         ;(display "find-rule" state rule)
         (cond ((markov-match state (car rule))
@@ -1111,8 +1113,29 @@
   '((if (null count)
         (setf count len))))
 
+(defun markov-general-rule-p (rule)
+  (let ((pre (car rule)))
+    (cond ((< (length pre) 2) nil) ;; 1st-order mm
+          (t
+           ;; return false if any member not *
+           ;; return t if all members are *
+           (dolist (s pre t)
+             (if (eq s '*) t (return nil)))))))
+
+(defun markov-find-state-leading-to (target rules)
+  (let (candidates)
+    (dolist (rule rules)
+      (let ((targets (cdr rule)))
+        (dolist (targ targets)
+          (cond ((eql (car targ) target)
+                 (push (car rule) candidates))))))
+    (cond (candidates ;; found at least one
+           (nth (random (length candidates)) candidates))
+          (t
+           nil))))
+
 (send markov-class :answer :advance '()
-  '((let (rule sum target rslt)
+  '((let (rule sum target rslt new-state)
       ;(display "markov" pattern rules)
       (setf rule (send self :find-rule))
       ;(display "advance 1" rule)
@@ -1121,6 +1144,21 @@
       (setf sum (markov-sum-of-weights rule))
       ;; the target can be a pattern, so apply NEXT to it
       (setf target (next (markov-pick-target sum rule)))
+      ;; if the matching rule is multiple *'s, then this
+      ;; is a higher-order Markov model, and we may now
+      ;; wander around in parts of the state space that
+      ;; never appeared in the training data. To avoid this
+      ;; we violate the strict interpretation of the rules
+      ;; and pick a random state sequence from the rule set
+      ;; that might have let to the current state. We jam
+      ;; this state sequence into state so that when we
+      ;; append target, we'll have a history that might
+      ;; have a corresponding rule next time.
+      (cond ((markov-general-rule-p rule)
+             (setf new-state (markov-find-state-leading-to target rules))
+             (cond (new-state
+                    ;(display "state replacement" new-state target)
+                    (setf state new-state)))))
       (setf state (append (cdr state) (list target)))
       ;(display "markov next" rule sum target state)
       ;; target is the symbol for the current state. We can
@@ -1360,7 +1398,7 @@
        ;; stack if the list is sorted because (apparently) the pivot points
        ;; are not random.
        (cond ((not (score-sorted sg:seq))
-              (setf sg:seq (sort sg:seq #'event-before))))
+              (setf sg:seq (bigsort sg:seq #'event-before))))
        (cond ((and sg:seq (null sg:end))
               (setf sg:end (event-end (car (last sg:seq)))))
              ((null sg:end)
@@ -1519,7 +1557,72 @@
 (defun event-before (a b)
   (< (car a) (car b)))
   
-  
+;; bigsort -- a sort routine that avoids recursion in order
+;; to sort large lists without overflowing the evaluation stack
+;;
+;; Does not modify input list. Does not minimize cons-ing.
+;;
+;; Algorithm: first accumulate sorted sub-sequences into lists
+;; Then merge pairs iteratively until only one big list remains
+;; 
+(defun bigsort (lis cmp) ; sort lis using cmp function
+  ;; if (funcall cmp a b) then a and b are in order
+  (prog (rslt sub pairs)
+    ;; first, convert to sorted sublists stored on rslt
+    ;; accumulate sublists in sub
+   get-next-sub
+    (if (null lis) (go done-1))
+    (setf sub (list (car lis)))
+    (setf lis (cdr lis))
+   fill-sub
+    ;; invariant: sub is non-empty, in reverse order
+    (cond ((and lis (funcall cmp (car sub) (car lis)))
+           (setf sub (cons (car lis) sub))
+           (setf lis (cdr lis))
+           (go fill-sub)))
+    (setf sub (reverse sub)) ;; put sub in correct order
+    (setf rslt (cons sub rslt)) ;; build rslt in reverse order
+    (go get-next-sub)
+   done-1
+    ;; invariant: rslt is list of sorted sublists
+    (if (cdr rslt) nil (go done-2))
+    ;; invariant: rslt has at least one list
+    (setf pairs rslt)
+    (setf rslt nil)
+   merge-pairs    ;; merge a pair and save on rslt
+    (if (car pairs) nil (go end-of-pass)) ;; loop until all pairs merged
+    ;; invariant: pairs has at least one list
+    (setf list1 (car pairs)) ;; list1 is non-empty
+    (setf list2 (cadr pairs)) ;; list2 could be empty
+    (setf pairs (cddr pairs))
+    (cond (list2
+           (setf rslt (cons (list-merge list1 list2 cmp) rslt)))
+          (t
+           (setf rslt (cons list1 rslt))))
+    (go merge-pairs)
+   end-of-pass
+    (go done-1)
+   done-2
+    ;; invariant: rslt has one sorted list!
+    (return (car rslt))))
+
+(defun list-merge (list1 list2 cmp)
+  (prog (rslt)
+   merge-loop
+    (cond ((and list1 list2)
+           (cond ((funcall cmp (car list1) (car list2))
+                  (setf rslt (cons (car list1) rslt))
+                  (setf list1 (cdr list1)))
+                 (t
+                  (setf rslt (cons (car list2) rslt))
+                  (setf list2 (cdr list2)))))
+          (list1
+           (return (nconc (reverse rslt) list1)))
+          (t
+           (return (nconc (reverse rslt) list2))))
+    (go merge-loop)))  
+
+
 ;; SCORE-SORT -- sort a score into time order
 ;;
 (defun score-sort (score &optional (copy-flag t)) 
@@ -1527,7 +1630,7 @@
   (let ((begin-end (car score)))
     (setf score (cdr score))
     (if copy-flag (setf score (append score nil)))
-    (cons begin-end (sort score #'event-before))))
+    (cons begin-end (bigsort score #'event-before))))
   
 
 ;; PUSH-SORT -- insert an event in (reverse) sorted order

Index: sal.lsp
===================================================================
RCS file: /cvsroot/audacity/audacity-src/nyquist/sal.lsp,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -d -r1.1 -r1.2
--- sal.lsp     30 Jan 2009 00:54:45 -0000      1.1
+++ sal.lsp     5 Mar 2009 17:42:25 -0000       1.2
@@ -496,7 +496,7 @@
 ;; returns:
 ;;   if eval-flag, then nothing is returned
 ;;   otherwise, returns nil if an error is encountered
-;;   otherwise, returns a list (PROG p1 p2 p3 ...) where pn are lisp
+;;   otherwise, returns a list (PROGN p1 p2 p3 ...) where pn are lisp
 ;;      expressions
 ;;
 (defun sal-compile (input eval-flag multiple-statements filename)
@@ -534,7 +534,7 @@
                               (setf input remainder))
                              ;; see if we've compiled everything
                              ((and (not eval-flag) (not remainder))
-                              (return (cons 'prog (reverse rslt))))
+                              (return (cons 'progn (reverse rslt))))
                              ;; if eval but no more input, return
                              ((not remainder)
                               (return))))

Index: dspprims.lsp
===================================================================
RCS file: /cvsroot/audacity/audacity-src/nyquist/dspprims.lsp,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -d -r1.5 -r1.6
--- dspprims.lsp        31 Jan 2009 11:12:15 -0000      1.5
+++ dspprims.lsp        5 Mar 2009 17:42:25 -0000       1.6
@@ -327,7 +327,9 @@
 
 
 
-;;; fixed-parameter filters based on snd-biquadfilt
+;;; fixed-parameter filters based on snd-biquad
+;;; note: snd-biquad is implemented in biquadfilt.[ch],
+;;; while BiQuad.{cpp,h} is part of STK
 
 (setf Pi 3.14159265358979)
 
@@ -335,7 +337,7 @@
 (defun sinh (x) (* 0.5 (- (exp x) (exp (- x)))))
 
 
-; remember that snd-biquadfilt uses the opposite sign convention for a_i's 
+; remember that snd-biquad uses the opposite sign convention for a_i's 
 ; than Matlab does.
 
 ; convenient biquad: normalize a0, and use zero initial conditions.

Index: nyinit.lsp
===================================================================
RCS file: /cvsroot/audacity/audacity-src/nyquist/nyinit.lsp,v
retrieving revision 1.7
retrieving revision 1.8
diff -u -d -r1.7 -r1.8
--- nyinit.lsp  24 Feb 2009 17:15:21 -0000      1.7
+++ nyinit.lsp  5 Mar 2009 17:42:25 -0000       1.8
@@ -31,8 +31,8 @@
 
 (format t "~%Nyquist -- A Language for Sound Synthesis and Composition~%")
 (format t "    Copyright (c) 1991,1992,1995,2007-2009 by Roger B. 
Dannenberg~%")
-(format t "    Version 3.02~%~%")
+(format t "    Version 3.03~%~%")
 
 ;(setf *gc-flag* t)
 
-'*scratch*;; create a symbol where Audacity plug-ins can save properties from 
one run to the next 
+

Index: nyquist.lsp
===================================================================
RCS file: /cvsroot/audacity/audacity-src/nyquist/nyquist.lsp,v
retrieving revision 1.7
retrieving revision 1.8
diff -u -d -r1.7 -r1.8
--- nyquist.lsp 30 Jan 2009 00:54:45 -0000      1.7
+++ nyquist.lsp 5 Mar 2009 17:42:25 -0000       1.8
@@ -719,40 +719,83 @@
 
 
 ; s-plot -- compute and write n data points for plotting
-; 
-(defun s-plot (snd &optional (n 1000) (dur 2.0))
-  (prog ((points (snd-samples snd (1+ n)))
-        (t0 (snd-t0 snd))
-        (filename (soundfilename *default-plot-file*))
-     outf
-     (period (/ 1.0 (snd-srate snd)))
-     len 
-     (maximum 1.0))
-    (setf outf (open filename :direction :output))
-    (cond ((null outf)
-       (format t "s-plot: could not open ~A!~%" filename)
-       (return nil)))
+;
+; dur is how many seconds of sound to plot. If necessary, cut the
+;     sample rate to allow plotting dur seconds
+; n is the number of points to plot. If there are more than n points,
+;     cut the sample rate. If there are fewer than n samples, just
+;     plot the points that exist.
+;
+(defun s-plot (snd &optional (dur 2.0) (n 1000))
+  (prog* ((sr (snd-srate snd))
+          (t0 (snd-t0 snd))
+          (filename (soundfilename *default-plot-file*))
+          (s snd) ;; s is either snd or resampled copy of snd
+          (outf (open filename :direction :output)) ;; for plot data
+          (maximum -1000000.0) ;; maximum amplitude
+          (minimum  1000000.0) ;; minimum amplitude
+          actual-dur ;; is the actual-duration of snd
+          sample-count ;; is how many samples to get from s
+          period  ;; is the period of samples to be plotted
+          truncation-flag     ;; true if we didn't get whole sound
+          points) ;; is array of samples
+     ;; If we need more than n samples to get dur seconds, resample
+     (cond ((< n (* dur sr))
+            (setf s (force-srate (/ (float n) dur) snd))))
+     ;; Get samples from the signal
+     (setf points (snd-samples s (1+ n)))
+     ;; If we got fewer than n points, we can at least estimate the
+     ;; actual duration (we might not know exactly if we use a lowered
+     ;; sample rate). If the actual sample rate was lowered to avoid
+     ;; getting more than n samples, we can now raise the sample rate
+     ;; based on our estimate of the actual sample duration.
+     (display "test" (length points) n)
+     (cond ((< (length points) n)
+            ;; sound is shorter than dur, estimate actual length
+            (setf actual-dur (/ (length points) (snd-srate s)))
+            (setf sample-count (round (min n (* actual-dur sr))))
+            (cond ((< n (* actual-dur sr))
+                   (setf s (force-srate (/ (float n) actual-dur) snd)))
+                  (t ;; we can use original signal
+                   (setf s snd)))
+            (setf points (snd-samples s sample-count))
+            ;; due to rounding, need to recalculate exact count
+            (setf sample-count (length points)))
+           ((= (length points) n)
+            (setf actual-dur dur)
+            (setf sample-count n))
+           (t ;; greater than n points, so we must have truncated sound
+            (setf actual-dur dur)
+            (setf sample-count n)
+            (setf truncation-flag t)))
+     ;; actual-dur is the duration of the plot
+     ;; sample-count is how many samples we have
+     (setf period (/ 1.0 (snd-srate s)))
+     (cond ((null outf)
+            (format t "s-plot: could not open ~A!~%" filename)
+            (return nil)))
     (format t "s-plot: writing ~A ... ~%" filename)
-    (setf len (length points))
-    (display "s-plot" snd (snd-srate snd) period n dur)
-    (cond ((and (> len n) (> (snd-srate snd) (/ n dur)))
-           (format t "WARNING: RESAMPLING TO ~A Hz~%" (/ n dur))
-          (setf points (snd-samples (force-srate (/ n dur) snd) (1+ n)))
-           (setf period (/ (float dur) n))
-           (setf len (length points))))
-    (cond ((> len n)
-       (setf len n)
-       (format t "WARNING: SOUND TRUNCATED TO ~A POINTS~%" len)
-       (format t "  consider (S-PLOT snd num-points duration)~%")))
-    (dotimes (i len)
-      (cond ((< (abs maximum) (abs (aref points i)))
-         (setf maximum (aref points i))))
+    (cond (truncation-flag
+           (format t "        !!TRUNCATING SOUND TO ~As\n" actual-dur)))
+    (cond ((/= (snd-srate s) (snd-srate snd))
+           (format t "        !!RESAMPLING SOUND FROM ~A to ~Ahz\n"
+                   (snd-srate snd) (snd-srate s))))
+    (cond (truncation-flag
+           (format t "        Plotting ~As, actual sound duration is greater\n"
+                     actual-dur))
+          (t
+           (format t "        Sound duration is ~As~%" actual-dur)))
+    (dotimes (i sample-count)
+      (setf maximum (max maximum (aref points i)))
+      (setf minimum (min minimum (aref points i)))
       (format outf "~A ~A~%" (+ t0 (* i period)) (aref points i)))
     (close outf)
-    (cond ((> (abs maximum) 1.0)
-       (format t "WARNING: MAXIMUM AMPLITUDE IS ~A~%" maximum)))
-    (format t "~A points from ~A to ~A~%"
-     len t0 (+ t0 (* len period)))))
+    (format t "        Wrote ~A points from ~As to ~As~%" 
+              sample-count t0 (+ t0 actual-dur))
+    (format t "        Range of values ~A to ~A\n" minimum maximum)
+    (cond ((or (< minimum -1) (> maximum 1))
+           (format t "        !!SIGNAL EXCEEDS +/-1~%")))))
+
 
 ; run something like this to plot the points:
 ; graph < points.dat | plot -Ttek


------------------------------------------------------------------------------
Open Source Business Conference (OSBC), March 24-25, 2009, San Francisco, CA
-OSBC tackles the biggest issue in open source: Open Sourcing the Enterprise
-Strategies to boost innovation and cut costs with open source participation
-Receive a $600 discount off the registration fee with the source code: SFAD
http://p.sf.net/sfu/XcvMzF8H
_______________________________________________
Audacity-cvs mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/audacity-cvs

Reply via email to