Add tasks for all the new languages
This commit is contained in:
parent
9dc3c2bb62
commit
bba7bfd280
13208 changed files with 134745 additions and 0 deletions
|
|
@ -0,0 +1,54 @@
|
|||
(lib 'struct)
|
||||
(lib 'sql)
|
||||
(lib 'hash)
|
||||
|
||||
(define H (make-hash))
|
||||
(define T (make-table (struct goodies (name poids valeur qty))))
|
||||
(define IDX (make-vector 0))
|
||||
|
||||
|
||||
;; convert to 0/1 PB
|
||||
;; transorm vector [1 2 3 4 (n-max 3) 5 (n-max 2) 6 .. ]
|
||||
;; into vector of repeated indices : [1 2 3 4 4 4 5 5 6 ... ]
|
||||
|
||||
(define (make-01 T)
|
||||
(for ((record T) (i (in-naturals)))
|
||||
(for ((j (in-range 0 (goodies-qty record))))
|
||||
(vector-push IDX i)))
|
||||
IDX)
|
||||
|
||||
(define-syntax-rule (name i) (table-xref T (vector-ref IDX i) 0))
|
||||
(define-syntax-rule (poids i) (table-xref T (vector-ref IDX i) 1))
|
||||
(define-syntax-rule (valeur i) (table-xref T (vector-ref IDX i) 2))
|
||||
|
||||
;;
|
||||
;; code identical to 0/1 problem
|
||||
;;
|
||||
|
||||
;; make an unique hash-key from (i rest)
|
||||
(define (t-idx i r) (string-append i "|" r))
|
||||
;; retrieve best core for item i, remaining r availbble weight
|
||||
(define (t-get i r) (or (hash-ref H (t-idx i r)) 0))
|
||||
|
||||
;; compute best score (i), assuming best (i-1 rest) is known
|
||||
(define (score i restant)
|
||||
(if (< i 0) 0
|
||||
(hash-ref! H (t-idx i restant)
|
||||
(if ( >= restant (poids i))
|
||||
(max
|
||||
(score (1- i) restant)
|
||||
(+ (score (1- i) (- restant (poids i))) (valeur i)))
|
||||
(score (1- i) restant)) ;; else not enough
|
||||
)))
|
||||
|
||||
;; compute best scores, starting from last item
|
||||
(define (task W)
|
||||
(define restant W)
|
||||
(make-01 T)
|
||||
(define N (1- (vector-length IDX)))
|
||||
(writeln 'total-value (score N W))
|
||||
(group
|
||||
(for/list ((i (in-range N -1 -1)))
|
||||
#:continue (= (t-get i restant) (t-get (1- i) restant))
|
||||
(set! restant (- restant (poids i)))
|
||||
(name i))))
|
||||
|
|
@ -0,0 +1,19 @@
|
|||
(define goodies
|
||||
'((map 9 150 1) (compass 13 35 1)(water 153 200 3)
|
||||
(sandwich 50 60 2)(🍰-glucose 15 60 2)(tin 68 45 3)
|
||||
(🍌-banana 27 60 3)(🍎-apple 39 40 3)(cheese 23 30 1)
|
||||
(beer 52 10 3)(🌞-suntan-cream 11 70 1)(camera 32 30 1)
|
||||
(t-shirt 24 15 2)(trousers 48 10 2)(umbrella 73 40 1)
|
||||
(☔️-trousers 42 70 1)(☔️--overcoat 43 75 1)(note-case 22 80 1)
|
||||
(🌞-sunglasses 7 20 1)(towel 18 12 2)(socks 4 50 1)
|
||||
(book 30 10 2)))
|
||||
|
||||
(list->table goodies T)
|
||||
|
||||
(task 400)
|
||||
total-value 1010
|
||||
→ ((socks) (🌞-sunglasses) (note-case) (☔️--overcoat) (🌞-suntan-cream) (cheese)
|
||||
(🍌-banana 🍌-banana 🍌-banana) (🍰-glucose 🍰-glucose) (water) (compass) (map))
|
||||
|
||||
(length (hash-keys H))
|
||||
→ 10827 ;; # of entries in cache
|
||||
|
|
@ -0,0 +1,67 @@
|
|||
var raw = <<'TABLE'
|
||||
map 9 150 1
|
||||
compass 13 35 1
|
||||
water 153 200 2
|
||||
sandwich 50 60 2
|
||||
glucose 15 60 2
|
||||
tin 68 45 3
|
||||
banana 27 60 3
|
||||
apple 39 40 3
|
||||
cheese 23 30 1
|
||||
beer 52 10 1
|
||||
suntancream 11 70 1
|
||||
camera 32 30 1
|
||||
T-shirt 24 15 2
|
||||
trousers 48 10 2
|
||||
umbrella 73 40 1
|
||||
w_trousers 42 70 1
|
||||
w_overcoat 43 75 1
|
||||
note-case 22 80 1
|
||||
sunglasses 7 20 1
|
||||
towel 18 12 2
|
||||
socks 4 50 1
|
||||
book 30 10 2
|
||||
TABLE
|
||||
|
||||
struct KnapsackItem {
|
||||
String name,
|
||||
Number weight,
|
||||
Number value,
|
||||
Number quant,
|
||||
}
|
||||
|
||||
var items = []
|
||||
raw.each_line{ |row|
|
||||
var fields = row.words;
|
||||
items << KnapsackItem(
|
||||
name: fields[0],
|
||||
weight: fields[1].to_n,
|
||||
value: fields[2].to_n,
|
||||
quant: fields[3].to_n,
|
||||
)
|
||||
}
|
||||
|
||||
func pick(weight, pos) is cached {
|
||||
|
||||
if (pos.is_neg || weight.is_neg || weight.is_zero) {
|
||||
return (0, 0, [])
|
||||
}
|
||||
|
||||
var (bv=0, bi=0, bw=0, bp=[])
|
||||
var item = items[pos];
|
||||
|
||||
for i in range(0, item.quant) {
|
||||
break if (i*item.weight > weight)
|
||||
var (v, w, p) = pick(weight - i*item.weight, pos.dec)
|
||||
next if ((v += i*item.value) <= bv)
|
||||
(bv, bi, bw, bp) = (v, i, w, p)
|
||||
}
|
||||
|
||||
(bv, bw + bi*item.weight, [bp..., bi])
|
||||
}
|
||||
|
||||
var (v, w, p) = pick(400, items.end)
|
||||
p.range.each { |i|
|
||||
say "#{p[i]} of #{items[i].name}" if p[i].is_pos
|
||||
}
|
||||
say "Value: #{v}; Weight: #{w}"
|
||||
Loading…
Add table
Add a link
Reference in a new issue