Permutaciones de números en Golang, la recursión no funciona.
Aquí está el código:
package main
import "fmt"
func anon(n []int, sl []int, result [][]int) {
if len(n) == 0 {
result = append(result, sl)
fmt.Printf("resultado %v\n", result)
return
}
for i , _ := range n {
fmt.Printf("n %v\n", n)
sl = append(sl, n[i])
ab := append(n[:i], n[i+1:]...)
fmt.Printf("i %v --- ab %v, sl %v, result %v ---\n",i, ab,sl,result )
anon(ab, sl , result)
}
}
func permute(nums []int) [][]int {
var sl1 = []int{}
var result = [][]int{}
anon(nums, sl1, result)
return result
}
func main() {
sl2 := []int{1,2}
permute(sl2)
}
Espero ‘resultado’ como [[1,2], [2,1]]. Sin embargo, al ver la siguiente salida del código ejecutado:
n [1 2]
i 0 --- ab [2], sl [1], result [] ---
n [2]
i 0 --- ab [], sl [1 2], result [] ---
resultado [[1 2]]
Veamos que para (en negrita) i=1, tengo ab[2], sl[1 2], result[] y n[2,2]. No puedo hacerlo funcionar con Golang. Algo similar funciona bien con Python.
Gracias por responder.
davy.ai
Según el código proporcionado, hay algunos problemas a señalar que podrían dar lugar a resultados inesperados:
anon
debería devolver la versión modificada de la listaresult
en lugar de simplemente agregar valores a ella. Esto se debe a que las listas en Go se pasan por valor, por lo que cuando la listaresult
se modifica dentro deanon
, no refleja los cambios fuera de la función.Dado que la lista
result
se modifica a lo largo de la recursión, es mejor utilizar un puntero a ella para que las modificaciones se realicen en la misma lista subyacente. Para hacer esto, la funciónanon
debería recibir un punteroresult *[][]int
en lugar de una listaresult [][]int
.En la función
anon
, cuando se agregan[i]
asl
, estamos modificando el mismo arreglo subyacente quen
, ya que las listas en Go son solo vistas de arreglos de respaldo. Esto puede llevar a un comportamiento inesperado, como tener valores duplicados en la listasl
. Para evitar esto, debemos hacer una copia de la listasl
utilizando la funciónappend
.Aquí tienes una versión actualizada del código que aborda estos problemas:
Esta versión del código debería producir el resultado
[[1 2] [2 1]]
. Nota que agregué una llamada afmt.Println
enmain
para imprimir el resultado de la funciónpermute
, y que agregué un paso de “retroceso” para eliminar el último elemento de la listasl
, de modo que no acumulemos valores entre diferentes ramas recursivas.