我正在尝试使用swift构建一个函数来映射数组,将数组中的每个值除以3,然后吐出一个新数组.这是我到目前为止:
func divideby3Map<T, U>(y: [T], z: T -> U) -> [U] {
let array = [int]()
let divideby3Array = array.map { [y] / 3 }
return dividedby3Array
}
divideby3Map([1,2,3,4,5])
Run Code Online (Sandbox Code Playgroud)
凡T和U是原始数组,分别返回的新阵列,它的使用泛型来完成.
我确定这不是正确编写的,我坚持正确的语法.例如,由于返回的数组由泛型表示[U],我假设我必须在返回的数组中的某处使用它,但不确定在哪里.
在编写泛型函数时,有时更容易通过3个步骤来处理它:首先使用特定类型单独编写代码.然后将代码编写为函数,仍然使用特定类型.最后,将功能更改为通用.
第一部分,将数组除以3,可以这样做:
let a = [1,2,3,4,5]
// map is run on the array of integers, and returns a new
// array with the operation performed on each element in a:
let b = a.map { $0 / 3 }
// so b will be [0,0,1,1,1]
// (don’t forget, integer division truncates)
Run Code Online (Sandbox Code Playgroud)
请注意,您提供的闭包{ }是一个将应用于数组的每个元素的操作. $0表示元素,并将其除以3.您也可以将其写为a.map { i in i / 3 }.
把它放到自己的功能中:
func divideby3Map(source: [Int]) -> [Int] {
return source.map { $0 / 3 }
}
Run Code Online (Sandbox Code Playgroud)
无需声明一个新数组 - map将为您创建一个.然后您可以直接返回(如果您愿意,可以将其分配给临时,但这不是必需的).
最后,如果要将其设为通用,请首先添加占位符:
func divideby3Map<T>(source: [T]) -> [T] {
return source.map { $0 / 3 }
}
Run Code Online (Sandbox Code Playgroud)
请注意,只需要一个占位符,T因为您返回的是与传入的完全相同的类型.
除非......这不会编译,因为编译器不知道T是保证提供两个重要的东西:分(一的能力/运营商),并创造新的能力T包括从整数(即创建一个T具有价值3,以被除以).否则,如果我们传递一个字符串数组或一个数组数组怎么办?
为此,我们需要"约束",T以便我们的函数只接受提供这些功能的参数类型.我们可以用它来约束一个这样的协议T是IntegerType,它不保证这些功能(以及一些其他的像+,*等):
func divideby3Map<T: IntegerType>(source: [T]) -> [T] {
return source.map { $0 / 3 }
}
divideby3Map(a) // returns [0,0,1,1,1]
let smallInts: [UInt8] = [3,6,9]
divideby3Map(smallInts) // returns [1,2,3]
Run Code Online (Sandbox Code Playgroud)