Golang数据结构算法之数组相关

提供的接口

  • 返回数组大小
  • 根据索引获取数组元素
  • 根据索引修改数组元素
  • 根据索引插入数组元素
  • 数组末尾追加元素(添加元素)
  • 清空数组
  • 根据索引删除数组元素
  • 返回数组字符串

首先定义一个数组结构体,结构体内容为数组内容以及数组大小,如下

type ArrayList struct {
	dataStore [] interface{} // 数组的存储
	TheSize int // 数组的大小
}

数组类型采用interface{}形式表示可以接收任何类型的数组,例如字符串和整型

编写数组初始化方法

func NewArrayList() *ArrayList {
	list := new(ArrayList) // 初始化结构体
	list.dataStore = make([]interface{},0,10) //开辟内存
	list.TheSize = 0
	return list
}

添加数组元素(追加数组)Append(),调用默认库的append方法,记得同步增加长度

func (list *ArrayList)Append(newval interface{}) {
	list.dataStore = append(list.dataStore,newval)
	list.TheSize++
}

根据索引获取数组元素

func (list *ArrayList) Get(index int) (interface{},error){
	if index < 0 || index >= list.TheSize {
		return nil,errors.New("索引越界")
	}
	return list.dataStore[index],nil
}

根据索引修改数组元素

func (list *ArrayList)Set(index int, newval interface{}) error{
	if index < 0 || index >= list.TheSize {
		return errors.New("索引越界")
	}
	list.dataStore[index] = newval // 对数据进行新值设置
	return nil
}

根据索引插入数组元素

func (list *ArrayList)Insert(index int, newval interface{}) error{
	if index < 0 || index >= list.TheSize {
		return errors.New("索引越界")
	}
	list.checkisFull() // 检测数组是否为满,是否需要开辟双倍内存
	list.dataStore = list.dataStore[:list.TheSize+1] // 插入数据,内存移动一位
	for i := list.TheSize;i > index;i--{ 
		list.dataStore[i] = list.dataStore[i-1]
	}
	list.dataStore[index] = newval 
	list.TheSize++ 
	return nil
}

插入方法有一个检测数组是否为满的方法,如果数组已经是满的时无法进行元素插入操作的,因为开辟内存时,默认数组10位,如果数组为满的话,开启双倍内存,以插入新元素,checkisFull()如下

func (list *ArrayList)checkisFull ()  {
	if list.TheSize == cap(list.dataStore) {
		newdataStore := make([]interface{},2*list.TheSize,2*list.TheSize) // 开辟双倍内存
		copy(newdataStore,list.dataStore) // 拷贝数据
		list.dataStore = newdataStore
	}
}

清空数组

func (list *ArrayList)Clear(){
	list.dataStore = make([]interface{},0,10)
	list.TheSize = 0
}

根据索引删除数组元素

func (list *ArrayList)Delete(index int) error{
	if index < 0 || index >= list.TheSize {
		return errors.New("索引越界")
	}
	list.dataStore = append(list.dataStore[:index],list.dataStore[index+1:]...)
	return nil
}

这里巧用了append方法,将要删除元素索引位置之前和之后的元素进行了拼接,返回的就是删除索引元素后的新数组

测试如下

func main() {
	var list ArrayList.List = ArrayList.NewArrayList()
	list.Append("a1")
	list.Append("b")
	list.Append("c")
	for i := 0; i < 10; i++ {
		list.Insert(1, "x")
		fmt.Println(list)
	}
}

输出如下

[a x b c]
[a x x b c]
[a x x x b c]
[a x x x x b c]
[a x x x x x b c]
[a x x x x x x b c]
[a x x x x x x x b c]
[a x x x x x x x x b c]
[a x x x x x x x x x b c]
[a x x x x x x x x x x b c]

Process finished with exit code 0

可见是开辟了双倍内存后的插入