diff --git a/src/slices/slices.go b/src/slices/slices.go index 1a837c53c19061..d958fe208b53e6 100644 --- a/src/slices/slices.go +++ b/src/slices/slices.go @@ -137,6 +137,17 @@ func Clone[S ~[]E, E any](s S) S { return append(S([]E{}), s...) } +// CloneFunc creates a transposition of the slice using f to create each +// corresponding element. May be used for creating a deep copy of s by supplying +// an f that creates a deep copy of each element. +func CloneFunc[S any, R any](s []S, f func(S) R) []R { + r := make([]R, len(s)) + for i := 0; i < len(s); i++ { + r[i] = f(s[i]) + } + return r +} + // Compact replaces consecutive runs of equal elements with a single copy. // This is like the uniq command found on Unix. // Compact modifies the contents of the slice s; it does not create a new slice. diff --git a/src/slices/slices_test.go b/src/slices/slices_test.go index 80efb34fc8a718..14b3cac89219f2 100644 --- a/src/slices/slices_test.go +++ b/src/slices/slices_test.go @@ -351,6 +351,17 @@ func TestClone(t *testing.T) { } } +func TestCloneFunc(t *testing.T) { + s1 := []byte{65, 66, 67} + s2 := CloneFunc[byte, string](s1, func(c byte) string { + return string(c) + }) + want := []string{"A", "B", "C"} + if !Equal(s2, want) { + t.Errorf("CloneFunc(%v) = %#v, want %#v", s1, s2, want) + } +} + var compactTests = []struct { name string s []int