2014-05-22 50 views
4

我有一個WorkDay結構,它保存有關某人工作的時間的數據,一個WorkWeek結構以保存一堆WorkDays,以及一個WorkMonth結構來保存一堆WorkWeeks。這個想法是讓每個人都返回在此期間工作的總小時數。Go - 圍繞界面切片問題的習慣方式

type WorkDay struct { 
    StartTime time.Time 
    EndTime time.Time 
} 

type WorkWeek struct { 
    WorkDays []WorkDay 
} 

type WorkMonth struct { 
    WorkWeeks []WorkWeek 
} 

func (w WorkDay) HoursWorked() time.Duration { 
    // Find hours worked through simple subtraction. 
} 

func (w WorkWeek) HoursWorked() time.Duration { 
    var totalHours time.Duration 
    for _, day := range w.WorkDays { 
     totalHours += day.HoursWorked() 
    } 
    return totalHours 
} 

func (w WorkMonth) HoursWorked() time.Duration { 
    var totalHours time.Duration 
    for _, week := range w.WorkWeeks { 
     totalHours += week.HoursWorked() 
    } 
    return totalHours 
} 

此代碼工作得很好,但在WorkWeek.HoursWorked()WorkMonth.HoursWorked()重複真正研我的齒輪。我試圖做到以下幾點,以爲我是很聰明:

func (w WorkWeek) HoursWorked() time.Duration { 
    return sumHoursWorked(w.WorkDays) 
} 

func (m WorkMonth) HoursWorked() time.Duration { 
    return sumHoursWorked(m.WorkWeeks) 
} 

type countable interface { 
    HoursWorked() time.Duration 
} 

func sumHoursWorked(timeFrames []countable) time.Duration { 
    var totalHours time.Duration 
    for _, frame := range timeFrames { 
     totalHours += frame.HoursWorked() 
    } 
    return totalHours 
} 

然而,正如解釋here,即使WorkDay實現countableWorkDay秒的片不計入的countable個切片。

那麼,是否有一些漂亮的,習慣性的方式擺脫這種情況,我錯過了,或者我只是堅持重複?

+0

您如何處理財政月份包含經常不完整的財政週數可變的數量?看起來像WorkMonth直接包含[] WorkDay,並且有些方法在必要時提取星期,這將是一個更簡單的實現。 – krait

+0

你是對的。這個計劃主要是爲了練習,但如果我要進一步研究它,我可能會重新思考我的類型,正如Volker在下面所建議的。 – sozorogami

回答

4

不是。要麼有一個countables分片,它給你動態方法調度或一些編程(你的第一個解決方案)或重構你的類型。我不知道你的問題領域,但由幾個星期組成的幾個月似乎很奇怪,至少每月/每週的東西。

2

否,因爲countables是另一種類型。 您可以定義自己的切片類型,併爲其添加添加方法。

func (w WorkWeek) HoursWorked() time.Duration { 
    return sumHoursWorked(w.WorkDays) 
} 

func (m WorkMonth) HoursWorked() time.Duration { 
    return sumHoursWorked(m.WorkWeeks) 
} 

type countable interface { 
    HoursWorked() time.Duration 
} 

type SliceCountable []countable 

func (m *SliceCountable) Add(c countable) { 
    *m = append(*m, c) 
} 

func (m SliceCountable) HoursWorked() time.Duration { 
var totalHours time.Duration 
for _, frame := range m { 
    totalHours += frame.HoursWorked() 
} 
return totalHours 
} 


func sumHoursWorked(timeFrames []countable) time.Duration { 
    var totalHours time.Duration 
    for _, frame := range timeFrames { 
     totalHours += frame.HoursWorked() 
    } 
    return totalHours 
}