2024 学习计划

2024 学习计划

一、编程语言

1、C

2、.NET

3、Java

4、Python

二、数据结构

1、数组(Arrays)

  • 介绍:
  • 实现一个动态数组(可自动调整大小的可变数组):
    •  练习使用数组和指针去编码,并且指针是通过计算去跳转而不是使用索引
    • 通过分配内存来新建一个原生数据型数组
      • 可以使用 int 类型的数组,但不能使用其语法特性
      • 从大小为16或更大的数(使用2的倍数 —— 16、32、64、128)开始编写
    •  size() —— 数组元素的个数
    •  capacity() —— 可容纳元素的个数
    •  is_empty()
    •  at(index) —— 返回对应索引的元素,且若索引越界则愤然报错
    •  push(item)
    •  insert(index, item) —— 在指定索引中插入元素,并把后面的元素依次后移
    •  prepend(item) —— 可以使用上面的 insert 函数,传参 index 为 0
    •  pop() —— 删除在数组末端的元素,并返回其值
    •  delete(index) —— 删除指定索引的元素,并把后面的元素依次前移
    •  remove(item) —— 删除指定值的元素,并返回其索引(即使有多个元素)
    •  find(item) —— 寻找指定值的元素并返回其中第一个出现的元素其索引,若未找到则返回 -1
    • resize(new_capacity) // 私有函数
      • 若数组的大小到达其容积,则变大一倍
      • 获取元素后,若数组大小为其容积的1/4,则缩小一半
  • 时间复杂度
    • 在数组末端增加/删除、定位、更新元素,只允许占 O(1) 的时间复杂度(平摊(amortized)去分配内存以获取更多空间)
    • 在数组任何地方插入/移除元素,只允许 O(n) 的时间复杂度
  • 空间复杂度
    • 因为在内存中分配的空间邻近,所以有助于提高性能
    • 空间需求 = (大于或等于 n 的数组容积)* 元素的大小。即便空间需求为 2n,其空间复杂度仍然是 O(n)

2、链表(Linked Lists)

  • 介绍:
  •  C代码(视频) – 不是整个视频,只是关于Node结构和内存分配的部分。
  • 链表 vs 数组:
  •  为什么你需要避免使用链表(视频)
  • 的确:你需要关于“指向指针的指针”的相关知识:(因为当你传递一个指针到一个函数时, 该函数可能会改变指针所指向的地址)该页只是为了让你了解“指向指针的指针”这一概念。 但我并不推荐这种链式遍历的风格。因为,这种风格的代码,其可读性和可维护性太低。
  • 实现(我实现了使用尾指针以及没有使用尾指针这两种情况):
    •  size() —— 返回链表中数据元素的个数
    •  empty() —— 若链表为空则返回一个布尔值 true
    •  value_at(index) —— 返回第 n 个元素的值(从0开始计算)
    •  push_front(value) —— 添加元素到链表的首部
    •  pop_front() —— 删除首部元素并返回其值
    •  push_back(value) —— 添加元素到链表的尾部
    •  pop_back() —— 删除尾部元素并返回其值
    •  front() —— 返回首部元素的值
    •  back() —— 返回尾部元素的值
    •  insert(index, value) —— 插入值到指定的索引,并把当前索引的元素指向到新的元素
    •  erase(index) —— 删除指定索引的节点
    •  value_n_from_end(n) —— 返回倒数第 n 个节点的值
    •  reverse() —— 逆序链表
    •  remove_value(value) —— 删除链表中指定值的第一个元素
  • 双向链表

3、堆栈(Stack)

4、队列(Queue)

  • 队列(视频)
  •  原型队列/先进先出(FIFO)
  •  [Review] Queues in 3 minutes (video)
  • 使用含有尾部指针的链表来实现:
    • enqueue(value) —— 在尾部添加值
    • dequeue() —— 删除最早添加的元素并返回其值(首部元素)
    • empty()
  • 使用固定大小的数组实现:
    • enqueue(value) —— 在可容的情况下添加元素到尾部
    • dequeue() —— 删除最早添加的元素并返回其值
    • empty()
    • full()
  • 花销:
    • 在糟糕的实现情况下,使用链表所实现的队列,其入列和出列的时间复杂度将会是 O(n)。 因为,你需要找到下一个元素,以致循环整个队列
    • enqueue:O(1)(平摊(amortized)、链表和数组 [探测(probing)])
    • dequeue:O(1)(链表和数组)
    • empty:O(1)(链表和数组)

5、哈希表(Hash table)

6、按位运算(Bitwise operations)

7、树(Trees)

7、排序(Sorting)

8、图(Graphs)

9、递归(Recursion)

10、字典树(Tries)

11、动态规划(Dynamic Programming)

12、设计模式

  • 主要的设计模式:
    • 策略模式(strategy)
    • 单例模式(singleton)
    • 适配器模式(adapter)
    • 原型模式(prototype)
    • 装饰器模式(decorator)
    • 访问者模式(visitor)
    • 工厂模式,抽象工厂模式(factory, abstract factory)
    • 外观模式(facade)
    • 观察者模式(observer)
    • 代理模式(proxy)
    • 委托模式(delegate)
    • 命令模式(command)
    • 状态模式(state)
    • 备忘录模式(memento)
    • 迭代器模式(iterator)
    • 组合模式(composite)
    • 享元模式(flyweight)
  • 书籍:《Head First 设计模式》、《大话设计模式》

内容参考来源:https://github.com/jwasham/coding-interview-university/blob/main/translations/README-cn.md