view tools/segmentation/methods.lisp @ 75:6b2ac9eef629

Improved segmentation implementation (ta, MTP) darcs-hash:20070713112322-f76cc-42a6ead0d8822164af5554d11ca98f93a1f96359.gz
author David Lewis <d.lewis@gold.ac.uk>
date Fri, 13 Jul 2007 12:23:22 +0100
parents a98c2adfd420
children 4ad1427d46d8
line wrap: on
line source
(in-package "AMUSE-SEGMENTATION")

(defmethod boundary-time ((segmenter basic-segmenter) (object anchored-period-designator))
  (if (segments-beforep segmenter)
      (onset object)
      (cut-off object)))
(defmethod boundary-time (segmenter (object moment-designator))
  object)

;;;;;;;;;;;;;;;;;;;;;;;
;;; Seriously made-up stuff (= dodgy)

(defun map-segmenters (composition &key (start-boundary-segmenter nil) (end-boundary-segmenter nil))
  (cond
    ((and start-boundary-segmenter end-boundary-segmenter)
     (%map-non-contiguous-segmenters composition start-boundary-segmenter end-boundary-segmenter))
    (start-boundary-segmenter
     (%map-start-segmenter composition start-boundary-segmenter))
    (end-boundary-segmenter
     (%map-end-segmenter composition end-boundary-segmenter))
    (t (error "Map-segmenters called with no segmenters"))))

(defun %map-start-segmenter (composition segmenter)
  (let ((segments))
    (sequence:dosequence (event composition (progn
					      (setf (duration (car segments))
						    (duration (time- (cut-off composition)
								     (onset (car segments)))))
					      (reverse segments)))
      (when (> (boundary-strength segmenter event composition) 0)
	(when segments
	  (setf (duration (car segments))
		(duration (time- (boundary-time segmenter event)
				 (onset (car segments))))))
	(push (make-instance 'anchored-period
			     :time (timepoint (boundary-time segmenter event)))
	      segments)))))

(defun %map-end-segmenter (composition segmenter)
  (let ((segments (list (make-instance 'anchored-period :time (timepoint composition)))))
    (sequence:dosequence (event composition (reverse (cdr segments)))
      (when (> (boundary-strength segmenter event composition) 0)
	(setf (duration (car segments))
	      (duration (time- (boundary-time segmenter event)
			       (onset (car segments)))))
	(push (make-instance 'anchored-period
			     :time (timepoint (boundary-time segmenter event)))
	      segments)))))

(defun %map-non-contiguous-segmenters (composition start-boundary-segmenter end-boundary-segmenter)
  ;; FIXME: crappy queue implementation
  ;; FIXME: This only returns paired starts and ends. Should we
  ;; process unpaired boundaries?
  (let ((segments) (starts))
    (sequence:dosequence (event composition (reverse segments))
      (when (> (boundary-strength start-boundary-segmenter event composition) 0)
	(setf (cdr (last starts))
	      (list (boundary-time start-boundary-segmenter event))))
      (when (> (boundary-strength end-boundary-segmenter event composition) 0)
	(when starts
	  (push (make-instance 'anchored-period
			       :interval (amuse::duration (time- (boundary-time end-boundary-segmenter event)
								 (car starts)))
			       :time (timepoint (pop starts)))
		segments))))))