diff --git a/README.md b/README.md index 5bb503d..9954b8d 100644 --- a/README.md +++ b/README.md @@ -395,7 +395,7 @@ func DeleteByIndex(slice interface{}, start int, end ...int) (interface{}, error func Drop(slice interface{}, n int) interface{} //creates a slice with `n` elements dropped from the beginning when n > 0, or `n` elements dropped from the ending when n < 0 func Every(slice, function interface{}) bool //return true if all of the values in the slice pass the predicate function, function signature should be func(index int, value interface{}) bool func Filter(slice, function interface{}) interface{} //filter slice, function signature should be func(index int, value interface{}) bool -func Find(slice, function interface{}) interface{} //iterates over elements of slice, returning the first one that passes a truth test on function.function signature should be func(index int, value interface{}) bool . +func Find(slice, function interface{}) (interface{}, bool) //iterates over elements of slice, returning the first one that passes a truth test on function.function signature should be func(index int, value interface{}) bool . func FlattenDeep(slice interface{}) interface{} //flattens slice recursive func IntSlice(slice interface{}) ([]int, error) //convert value to int slice func InterfaceSlice(slice interface{}) []interface{} //convert value to interface{} slice diff --git a/README_zh-CN.md b/README_zh-CN.md index 6b07c88..1b7ce5a 100644 --- a/README_zh-CN.md +++ b/README_zh-CN.md @@ -395,7 +395,7 @@ func Difference(slice1, slice2 interface{}) interface{} //返回 func DeleteByIndex(slice interface{}, start int, end ...int) (interface{}, error) //删除切片中start到end位置的值 func Drop(slice interface{}, n int) interface{} //创建一个新切片,当n大于0时删除原切片前n个元素,当n小于0时删除原切片后n个元素 func Every(slice, function interface{}) bool //slice中所有元素都符合函数条件时返回true, 否则返回false. 函数签名:func(index int, value interface{}) bool -func Find(slice, function interface{}) interface{} //查找slice中第一个符合条件的元素,函数签名:func(index int, value interface{}) bool +func Find(slice, function interface{}) (interface{}, bool)//查找slice中第一个符合条件的元素,函数签名:func(index int, value interface{}) bool func Filter(slice, function interface{}) interface{} //过滤slice, 函数签名:func(index int, value interface{}) bool func FlattenDeep(slice interface{}) interface{} //将slice递归为一维切片。 func IntSlice(slice interface{}) ([]int, error) //转成int切片 diff --git a/slice/slice.go b/slice/slice.go index 8d17ab4..37d0a23 100644 --- a/slice/slice.go +++ b/slice/slice.go @@ -197,7 +197,7 @@ func GroupBy(slice, function interface{}) (interface{}, interface{}) { // Find iterates over elements of slice, returning the first one that passes a truth test on function. // The function signature should be func(index int, value interface{}) bool . -func Find(slice, function interface{}) interface{} { +func Find(slice, function interface{}) (interface{}, bool) { sv := sliceValue(slice) fn := functionValue(function) @@ -206,7 +206,7 @@ func Find(slice, function interface{}) interface{} { panic("function param should be of type func(int, " + elemType.String() + ")" + reflect.ValueOf(true).Type().String()) } - var index int + index := -1 for i := 0; i < sv.Len(); i++ { flag := fn.Call([]reflect.Value{reflect.ValueOf(i), sv.Index(i)})[0] if flag.Bool() { @@ -214,7 +214,13 @@ func Find(slice, function interface{}) interface{} { break } } - return sv.Index(index).Interface() + + if index == -1 { + var none interface{} + return none, false + } + + return sv.Index(index).Interface(), true } // FlattenDeep flattens slice recursive diff --git a/slice/slice_test.go b/slice/slice_test.go index 420cd4f..6dc9dbe 100644 --- a/slice/slice_test.go +++ b/slice/slice_test.go @@ -190,13 +190,28 @@ func TestFind(t *testing.T) { even := func(i, num int) bool { return num%2 == 0 } - res := Find(nums, even) + res, ok := Find(nums, even) + if !ok { + t.Fatal("found nothing") + } + if res != 2 { internal.LogFailedTestInfo(t, "Find", nums, 2, res) t.FailNow() } } +func TestFindFoundNothing(t *testing.T) { + nums := []int{1, 1, 1, 1, 1, 1} + findFunc := func(i, num int) bool { + return num > 1 + } + _, ok := Find(nums, findFunc) + if ok { + t.Fatal("found something") + } +} + func TestFlattenDeep(t *testing.T) { input := [][][]string{{{"a", "b"}}, {{"c", "d"}}} expected := []string{"a", "b", "c", "d"}