Распакуйте кортеж в другой кортеж
Предположим, мне нужно построить кортеж длины три:
(x , y, z)
И у меня есть функция, которая возвращает кортеж длины два - exampleFunction
и два последних элемента создаваемого кортежа взяты из этого кортежа.
Как я могу сделать это без необходимости звонить exampleFunction
два раза:
(x, fst exampleFunction , snd exampleFunction)
Я просто хочу сделать / достичь чего-то вроде
(x, exampleFunction)
но он жалуется, что кортежи имеют непревзойденную длину (конечно)
Не смотря на делать let y,z = exampleFunction()
4 ответа
Там может быть встроенная функция, но пользовательская будет работать так же хорошо.
let repack (a,(b,c)) = (a,b,c)
repack (x,exampleFunction)
Я не уверен, стоит ли отдельный ответ, но оба ответа, приведенные выше, не оптимальны, поскольку оба создают избыточность Tuple<'a, Tuple<'b, 'c>>
при вызове вспомогательной функции. Я бы сказал, что пользовательский оператор будет лучше как для удобочитаемости, так и для производительности:
let inline ( +@ ) a (b,c) = a, b, c
let result = x +@ yz // result is ('x, 'y, 'z)
Проблема в том, что функция возвращает a*b
поэтому тип возвращаемого значения становится 'a*('b*'c)
который отличается от 'a*'b*'c
лучшее решение - маленькая вспомогательная функция, такая как
let inline flatten (a,(b,c)) = a,b,c
тогда вы можете сделать
(x,examplefunction) |> flatten
У меня есть следующая функция в моем общем файле расширения. Вы можете найти это полезным.
let inline squash12 ((a,(b,c) ):('a*('b*'c) )):('a*'b*'c ) = (a,b,c )
let inline squash21 (((a,b),c ):(('a*'b)*'c )):('a*'b*'c ) = (a,b,c )
let inline squash13 ((a,(b,c,d)):('a*('b*'c*'d))):('a*'b*'c*'d) = (a,b,c,d)
let seqsquash12 (sa:seq<'a*('b*'c) >) = sa |> Seq.map squash12
let seqsquash21 (sa:seq<('a*'b)*'c >) = sa |> Seq.map squash21
let seqsquash13 (sa:seq<'a*('b*'c*'d)>) = sa |> Seq.map squash13
let arrsquash12 (sa:('a*('b*'c) ) array) = sa |> Array.map squash12
let arrsquash21 (sa:(('a*'b)*'c ) array) = sa |> Array.map squash21
let arrsquash13 (sa:('a*('b*'c*'d)) array) = sa |> Array.map squash13