ドント方式投票の計算

30分プログラム、その657。ドント方式投票の計算をやってみました。

新聞を読んでいたら「ドント式投票は、より民意が反映される」という趣旨のことが書いてありました。"民意が反映される"の意味はよく分からないですが、とりあえずコードを書いてみましょう。

ところで、ウィキペディアドント方式の例は間違っている気がします。正しくは、(A,B,C)=(3,2,2)だと思います。誰か教えてあげてください。あるいは、ボクに怒られないノートの書き方を教えてください。

使い方

gosh> (donto 8 (list (party 'a 1000)
	             (party 'b 700)
  		     (party 'c 600)
	             (party 'd 280)))

;; 各リストの第1要素が政党名、第3要素が議席数
((b 350/3 3) (c 300 2) (d 280 0) (a 500/3 3))

ソースコード

#! /opt/local/bin/gosh
;; -*- mode:scheme; coding:utf-8 -*-
;;
;; donto.scm -
;;
;; Copyright(C) 2009 by mzp
;; Author: MIZUNO Hiroki / mzpppp at gmail dot com
;; http://howdyworld.org
;;
;; Timestamp: 2009/09/10 21:47:58
;;
;; This program is free software; you can redistribute it and/or
;; modify it under MIT Lincence.
;;

(define (party name votes)
  (list name votes 0))

(define (party-name party)
  (car party))
(define (party-votes party)
  (cadr party))
(define (party-seats party)
  (caddr party))

(define (update party)
  (let1 s (+ 1 (party-seats party))
	(list (party-name party)
	      (/ (party-votes party) s)
	      s)))

(define (donto seats party-list)
  (if (= seats 0)
      party-list
      (let1 xs (sort party-list (lambda(x y) (> (party-votes x)
						(party-votes y))))
	    (donto (- seats 1)
		   (cons (update (car xs))
			 (cdr xs))))))


(donto 8 (list (party 'a 1000)
	       (party 'b 700)
	       (party 'c 600)
	       (party 'd 280)))