~rbn/fit

d4e952d1ef97f706723c91cd9a76734bafb01662 — Ruben Schuller 1 year, 3 months ago 2a06b6c
return errors for bin methods
4 files changed, 41 insertions(+), 21 deletions(-)

M bin.go
M pack.go
M strategy.go
M strategy_test.go
M bin.go => bin.go +9 -5
@@ 1,24 1,28 @@
package fit

import (
	"fmt"
)

type Bin struct {
	items    []Item
	size     int64
	capacity int64
}

func (b *Bin) add(i Item) {
func (b *Bin) add(i Item) error {
	if !b.fits(i) {
		return fmt.Errorf("item doesn't fit bin")
	}
	b.items = append(b.items, i)
	b.size += i.Size
	return nil
}

func (b *Bin) fits(i Item) bool {
	return b.size+i.Size <= b.capacity
}

//func newBin(capacity int64, i Item) Bin {
//	return Bin{items: []Item{i}, size: i.Size, capacity: capacity}
//}

func newBin(capacity int64) Bin {
	return Bin{capacity: capacity, items: []Item{}}
}

M pack.go => pack.go +5 -2
@@ 16,8 16,11 @@ func Pack(strategy StrategyFunc, capacity int64, items []Item) ([]Bin, error) {
		if x.Size > capacity {
			return nil, fmt.Errorf("%v exceeds capacity: size: %v capacity: %v", string(x.Data), x.Size, capacity)
		}

		bins = strategy(bins, capacity, x)
		var err error
		bins, err = strategy(bins, capacity, x)
		if err != nil {
			return nil, err
		}
	}

	return bins, nil

M strategy.go => strategy.go +22 -13
@@ 4,48 4,57 @@ import (
	"sort"
)

func First(bins []Bin, capacity int64, x Item) []Bin {
func First(bins []Bin, capacity int64, x Item) ([]Bin, error) {
	for i, b := range bins {
		if !b.fits(x) {
			continue
		}
		bins[i].add(x)
		return bins
		return bins, nil
	}
	n := newBin(capacity)
	n.add(x)
	err := n.add(x)
	if err != nil {
		return nil, err
	}
	bins = append(bins, n)
	return bins
	return bins, nil
}

func Best(bins []Bin, capacity int64, x Item) []Bin {
func Best(bins []Bin, capacity int64, x Item) ([]Bin, error) {
	sort.Sort(sort.Reverse(BinsBySize(bins)))
	for i, b := range bins {
		if !b.fits(x) {
			continue
		}
		bins[i].add(x)
		return bins
		err := bins[i].add(x)
		if err != nil {
			return nil, err
		}
		return bins, nil
	}
	n := newBin(capacity)
	n.add(x)
	bins = append(bins, n)
	return bins
	return bins, nil
}

func Worst(bins []Bin, capacity int64, x Item) []Bin {
func Worst(bins []Bin, capacity int64, x Item) ([]Bin, error) {
	sort.Sort(BinsBySize(bins))
	for i, b := range bins {
		if !b.fits(x) {
			continue
		}
		bins[i].add(x)
		return bins
		err := bins[i].add(x)
		if err != nil {
			return nil, err
		}
		return bins, nil
	}
	n := newBin(capacity)
	n.add(x)
	bins = append(bins, n)
	return bins
	return bins, nil
}

type StrategyFunc func([]Bin, int64, Item) []Bin
type StrategyFunc func([]Bin, int64, Item) ([]Bin, error)

M strategy_test.go => strategy_test.go +5 -1
@@ 100,7 100,11 @@ func testStrategy(t *testing.T, strategy StrategyFunc, tests []strategyTest) {
	bins := []Bin{}

	for _, test := range tests {
		bins = strategy(bins, 10, test.item)
		var err error
		bins, err = strategy(bins, 10, test.item)
		if err != nil {
			t.FailNow()
		}
		t.Logf("%#v",bins)

		binItem := bins[test.bin].Items()[test.pos]