Home > Mobile >  GOLANG Delete a slice from Slice of Slice
GOLANG Delete a slice from Slice of Slice

Time:07-31

I want to create function to delete a slice from slice of slice. It should take two inputs: 1. slice of slice (list var) and 2. slice to be deleted (eachsvc) as input. And return updated slice of slice (list var).

I am having issues with this code as it is not working with slice of slice. Any help is appreciated. Thanks.

func truncate_slice(list [][]string, eachsvc []string) [][]string {
    //find index of eachsvc in list
    i := indexOf(eachsvc, list)
    copy(list[i:], list[i 1:]) // Shift a[i 1:] left one index.
    list[len(list)-1] = ""     // Erase last element (write zero value).
    list = list[:len(list)-1]  // Truncate slice.
    return list
}

Func to get index of slice to be deleted from slice of slice

func indexOf(element []string, data [][]string) int {
    for k, v := range data {
        if element == v {
            return k
        }
    }
    return -1 //not found.
}

CodePudding user response:

Since you want to compare slices based on their elements (as you commented), you will first need to define a function to check equality of 2 given slices. Something like this:

func eq(s1, s2 []string) bool {
    if len(s1) != len(s2) {
        return false
    }
    s2Map := make(map[string]int)
    s1Map := make(map[string]int)
    for _, str := range s2 {
        s2Map[str]  = 1
    }
    for _, str := range s1 {
        s1Map[str]  = 1
    }
    for key, count := range s1Map {
        if count != s2Map[key] {
            return false
        }
    }
    return true
}

So in this case, ["John", "Doe"] is equal to ["Doe", "John"]. If you also want to check order, I would suggest you to use reflect.DeepEqual(slice1, slice2) instead of implementing one. By the way, using == to compare slices, means if they have the same reference, since slices are views over arrays basically.

CodePudding user response:

As AminMal has said, you can use "reflect.DeepEqual(slice1, slice2)" to compare the slices.

As per documentation:

Slice values are deeply equal when all of the following are true: they are both nil or both non-nil, they have the same length, and either they point to the same initial entry of the same underlying array (that is, &x[0] == &y[0]) or their corresponding elements (up to length) are deeply equal. Note that a non-nil empty slice and a nil slice (for example, []byte{} and []byte(nil)) are not deeply equal.

package main

import (
    "errors"
    "fmt"
    "reflect"
)

func main() {
    sl := [][]string{[]string{"test1"}, []string{"test1", "test2"}, []string{"test3"}}

    truncSlic, err := truncate_slice(sl, []string{"test3"})
    if err != nil {
        fmt.Println(err)
        return
    }
    fmt.Println(truncSlic)
}

func indexOf(element []string, data [][]string) int {
    for i, v := range data {
        if reflect.DeepEqual(element, v) { //compare two silces
            return i
        }

    }
    return -1
}

func truncate_slice(list [][]string, eachsvc []string) ([][]string, error) {
    //find index of eachsvc in list
    i := indexOf(eachsvc, list)
    if i == -1 {
        return nil, errors.New("Not Found")
    }
    copy(list[i:], list[i 1:]) // Shift a[i 1:] left one index.
    list[len(list)-1] = nil    // Erase last element (write zero value).
    list = list[:len(list)-1]  // Truncate slice.
    return list, nil
}

Output: [[test1] [test1 test2]]

  • Related