Algorithm data structure 02 / common data structures

Data structure 02 Algorithm 2 / common data structures

1. Stack

  • Characteristics: last-out data structure, end of the stack and the stack

  • Scenario: Each web browser has a back button. When browsing web pages, those pages are placed in a stack (actually the URL of the page). Now at the top of the page view, a view of the first page at the bottom. If you press the 'Back' button will reverse order just browse the pages.

  • Stack method:

    Stack():创建一个空的新栈。 它不需要参数,并返回一个空栈。
    push(item):将一个新项添加到栈的顶部。它需要 item 做参数并不返回任何内容。
    pop():从栈中删除顶部项。它不需要参数并返回 item 。栈被修改。
    peek():从栈返回顶部项,但不会删除它。不需要参数。 不修改栈。
    isEmpty():测试栈是否为空。不需要参数,并返回布尔值。
    size():返回栈中的 item 数量。不需要参数,并返回一个整数。
  • To implement a stack list

    class Stack():
        def __init__(self):
            self.items = []
        def push(self,item):
            """ 栈顶添加 """
            self.items.append(item)
        def pop(self):
            """ 栈顶删除 """
            return self.items.pop()
        def peek(self):
            """ 查看栈顶元素 """
            return self.items[-1]
        def isEmpty(self):
            """ 查看栈是否为空 """
            return self.items == []
        def size(self):
            """ 查看栈中元素个数 """
            return len(self.items)

2. Queue

  • Characteristics: FIFO data structure

  • Scenario: The computer lab has 30 computers and a printer networking. When students want to print their print jobs with all other print job is waiting for the "consistent." The first task is to complete the entry. If you are the last one, you have to wait for you in front of all other tasks Print

  • Queue method:

    Queue():创建一个空的新队列。 它不需要参数,并返回一个空队列。
    enqueue(item):将新项添加到队尾。 它需要 item 作为参数,并不返回任何内容。
    dequeue():从队首移除项。它不需要参数并返回 item。 队列被修改。
    isEmpty():查看队列是否为空。它不需要参数,并返回布尔值。
    size():返回队列中的项数。它不需要参数,并返回一个整数。
  • Implement a queue list

    class Queue():
        def __init__(self):
            self.items = []
        def enqueue(self,item):
            """ 队列尾部添加元素 """
            self.items.insert(0,item)
        def dequeue(self):
            """ 删除队列头部的元素 """
            return self.items.pop()
        def isEmpty(self):
            """ 查看队列是否为空 """
            return self.items == []
        def size(self):
            """ 查看队列中元素的个数 """
            return len(self.items)
  • Queue Application Example:

    烫手的山芋
    1.烫手山芋游戏介绍:
    6个孩子围城一个圈,排列顺序孩子们自己指定。第一个孩子手里有一个烫手的山芋,需要在计时器计时1秒后将山芋传递给下一个孩子,依次类推。规则是,在计时器每计时7秒时,手里有山芋的孩子退出游戏。该游戏直到剩下一个孩子时结束,最后剩下的孩子获胜。请使用队列实现该游戏策略,排在第几个位置最终会获胜。
    2.提取有价值的信息:
    计时1s的时候山芋在第一个孩子手里面
    山芋会被1s传递一次
    7秒钟山芋被传递了6次
    准则:保证第一个(队头)孩子手里面永远要有山芋,山芋不动、人动
    kids = ['A','B','C','D','E','F']
    q = Queue()
    for kid in kids:
        q.enqueue(kid)
    while q.size() > 1:  # 当队列中孩子的个数大于1游戏继续否则游戏结束
        for i in range(1,7): # 山芋传递的次数
            kid = q.dequeue()  # 对头元素出队列再入队列
            q.enqueue(kid)
        q.dequeue()  # 一轮游戏结束后,将对头孩子淘汰(对头孩子手里永远有山芋)
    print(q.dequeue())

3. deque

  • Features: Compared with the queue, there are two head and tail. Can insert and delete data in the dual port, a single data structure characteristic stacks and queues

  • Deque Method:

    Deque():创建一个空的新 deque。它不需要参数,并返回空的 deque。
    addFront(item):将一个新项添加到 deque 的首部。它需要 item 参数 并不返回任何内容。
    addRear(item):将一个新项添加到 deque 的尾部。它需要 item 参数并不返回任何内容。
    removeFront():从 deque 中删除首项。它不需要参数并返回 item。deque 被修改。
    removeRear():从 deque 中删除尾项。它不需要参数并返回 item。deque 被修改。
    isEmpty():测试 deque 是否为空。它不需要参数,并返回布尔值。
    size():返回 deque 中的项数。它不需要参数,并返回一个整数。
  • List implementation deque

    class Deque:
        def __init__(self):
            self.items = []
        def addFront(self,item):
            """ 双端队列头部添加 """
            self.items.insert(0,item)
        def addRear(self,item):
            """ 双端队列尾部添加 """
            self.items.append(item)
        def removeFront(self):
            """ 双端队列头部删除 """
            return self.items.pop(0)
        def removeRear(self):
            """ 双端队列尾部删除 """
            return self.items.pop()
        def isEmpty(self):
            """ 查看双端队列是否为空 """
            return self.items == []
        def size(self):
            """ 查看双端队列元素的个数 """
            return len(self.items)
  • Deque Application Example: determining whether a string is a palindrome

    deque = Deque()
    def huiwen(s):
        for i in s:
            deque.addFront(i)
        while deque.size() > 1:
            if deque.removeRear() != deque.removeFront():
                print('不是回文')
                return
        print('是回文')
    huiwen('12321')
    

4. memory-related

  • Visualize understanding of memory (memory size and address)

    1.开辟好的内存空间会有两个默认的属性:大小,地址
    2.大小:衡量该块内存能够存储数据的大小
      - bit(位):只可以存放一位二进制的数
      - byte(字节):8bit
      - kb:1024byte
      - 10Mb:10*1024*1024*8
      - 作用:可以衡量该内存存储数据大小的范围
    3.地址:16进制的数表示
      - 作用:定位内存空间的位置
      - 变量/引用:内存空间的地址
    
  • The concept of variables

    1.引用==变量,变量就是我们为存储数据单独开辟的内存空间。
    
    2.理解a=10的内存图(指向)
    如果一个变量表示的是某一块内存空间的地址,则该变量指向该块内存空间。
    如果一个变量指向了某一块内存空间,则该变量就可以代替/表示这块内存中存储的数值
    
  • The size of the memory space occupied by different data

    整数:4字节
    浮点型:float:4字节,double:8字节
    字符型(char):1字节
    

The order table

  • Structure of sequence table can be divided into two forms: a single data type, and multiple data types; Python lists and tuples belong to multiple data types order table

  • Single data type sequence table memory map (memory turned on continuously), an array as an example:

    Array

  • Multiple Data Types FIG sequence table memory (RAM discontinuous open), an example of a list:

    List

  • Malpractice sequence table

    Structure needs to know in advance the order table data size to apply continuous storage space, while performing the expansion time and the need for data relocation.

6. list

  • List brief:

    1. list (Linked list) is a common basic data structures, a linear table, as sequence table but not continuously stored data, but each node (data storing means) stored in a next node information (ie, address)

    2. When no data move relative to the order list, the list structure can take advantage of computer memory, dynamic memory management for flexible and be expanded.

  • List approach:

    is_empty():链表是否为空
    length():链表长度
    travel():遍历整个链表
    add(item):链表头部添加元素
    append(item):链表尾部添加元素
    insert(pos, item):指定位置添加元素
    remove(item):删除节点
    search(item):查找节点是否存在
    
  • Code

    class Node():
        """ 初始化一个节点 """
        def __init__(self,item):
            self.item = item   # 存储数值数据
            self.next = None   # 存储下一个节点的地址
    
    class Link():
        """ 构建一个空链表 """
        def __init__(self):
          self._head = None   # _head要指向第一个节点,如果没有节点则指向None
        def add(self,item):
            """ 链表头部添加元素 """
            node = Node(item)   # 1.创建一个新节点
            node.next = self._head   # 2.将创建新节点的next指向,指向原来的第一个节点
            self._head = node   # 3.将链表的_head指向新创建的节点
    
        def travel(self):
            """ 遍历链表 """
            # 在非空的链表中head永远要指向第一个节点的地址,永远不要修改它的指向,否则会造成数据的丢失
            cur = self.__head
            while cur:
                print(cur.item)
                cur = cur.next
    
         def is_empty(self):
            """ 判断链表是否为空 """
            return self._head == []
    
        def length(self):
            """ 查看链表的长度 """
            count = 0  # 记录节点的个数
            cur = self.__head
            while cur:
                count += 1
                cur = cur.next
            return count
    
         def append(self,item):
            """ 在链表的尾部添加元素 """
            node = Node(item)
            cur = self._head   # 当前结点
            pre = None    # 指向cur的前一个节点
            if self._head = None:  # 如果链表为空则需要单独处理
                self._head = node
                return
            while cur:
                pre = cur
                cur = cur.next  # 循环结束之后cur指向了None,pre指向了最后一个节点
            pre.next = node 
    
         def search(self,item):
            """ 在链表中查找元素 """
            cur = self._head
            find = False
            while cur:
                if cur.item == item:
                    find = True
                    break
                else:
                      cur = cur.next
            return find
    
        def insert(self,pos,item):
            """ 在链表中插入元素 """
            node = Node(item)
            cur = self._head
            pre = None
            # 如果插入的位置大于链表的长度,则默认插入到尾部
            if pos > self.items.length()-1:
                self.append(item)
                return
    
            for i in range(pos):
                pre = cur
                cur = cur.next
            pre.next = node
            node.next = cur
    
    
         def remove(self,item):
            """ 移除指定的元素 """
            cur = self._head
            pre = None
            if item == cur.item:
                self._head = cur.next
                return
    
            while cur:
                if cur.item != item:
                    pre = cur
                    cur = cur.next
                else:
                    break
            pre.next = cur.next
    

    FIG Memory chain structure:

    List

    Adding header list (the Add) memory map:

    The head of the list to add (add)

    Chain insert (insert) memory map:

    Insert list

7. Binary Tree

  • Binary Tree Overview:

    Binary tree: the root, leaf node

    2. The sub-tree: leaf node has left subtree is complete, only a single node is not complete sub-tree

    3. Conclusion:

    • A sub-tree root node contains a minimum of
    • A complete binary tree is constituted by a plurality of subtrees
    • A sub-child node of the tree may also represent another root subtree
  • Binary tree traversal

    广度遍历:逐层遍历
    深度遍历:纵向遍历,前中后表示的是子树种根节点的位置
       一定要基于子树去遍历
       前序遍历:根左右
       中序遍历:左根右
       后序遍历:左右根
    
    为什么用深度遍历:要结合排序二叉树一起使用,深度遍历可以帮我们二叉树进行排序。
    
  • Ordinary Binary Tree:

    class Node():
        def __init__(self,item):
            self.item = item
            self.left = None
            self.right = None
    
    class Tree():
        # 构建一棵空树
        def __init__(self):
            self.root = None
        def add(self,item):
            """ 插入节点 """
            if self.root == None:  # 向空树中插入第一个节点
                node = Node(item)
                self.root = node
                return
            else:  # 向非空的二叉树中插入一个节点
                node = Node(item)
                cur = self.root  # 防止根节点指向改变
                queue = [cur]
                while queue:
                    root = queue.pop(0)
                    if root.left != None:
                        queue.append(root.left)
                    else:
                        root.left = node
                        break
                    if root.right != None:
                        queue.append(root.right)
                    else:
                        root.right = node
                        break
    
        # 广度遍历
        def travel(self):
            """ 遍历二叉树 """
            cur = self.root
            queue = [cur]
            if self.root == None:
                print('')
                return
            while queue:
                root = queue.pop(0)
                print(root.item)
                if root.left != None:
                    queue.append(root.left)
                if root.right != None:
                    queue.append(root.right)
    
        # 深度遍历
        def forward(self,root):
            """ 前序遍历 """
            if root == None:
                return
            print(root.item)
            self.forward(root.left)
            self.forward(root.right)
        def middle(self,root):
            """ 中序遍历 """
            if root == None:
                return     
            self.middle(root.left)
            print(root.item)
            self.middle(root.right)
        def back(self,root):
            """ 后序遍历 """
            if root == None:
                return
            self.back(root.left)
            self.back(root.right)
            print(root.item)
    
  • Sort Binary Tree:

    # 排序二叉树
    class SortTree():
        def __init__(self):
            self.root = None
        def add(self,item):
            node = Node(item)
            cur = self.root
            if self.root == None:
                self.root = node
                return
            while True:
                # 插入节点的值小于根节点的值,往根节点左侧插
                if node.item < cur.item:
                    if cur.left == None:
                        cur.left = node
                        break
                    else:
                        cur = cur.left
                else: # 插入节点的值大于根节点,往根节点右侧插
                    if cur.right == None:
                        cur.right = node
                        break 
                    else:
                        cur = cur.right
        def middle(self,root):
            """ 中序遍历 """
            if root == None:
                return     
            self.middle(root.left)
            print(root.item)
            self.middle(root.right)
    
    tree = SortTree()
    alist = [3,8,4,6,7,8]
    for i in alist:
        tree.add(i)
    tree.middle(tree.root)
    

Guess you like

Origin www.cnblogs.com/liubing8/p/12059431.html