1. 程式人生 > 其它 >2022.01.2-redis為什麼這麼快

2022.01.2-redis為什麼這麼快

今天打了周賽,第四道hard周賽結束才過,菜雞如我

參加會議的最多員工數

class Solution:
    def maximumInvitations(self, fa: List[int]) -> int:
        n = len(fa)
        pre = defaultdict(list)
        cnt =[0] * n
        for i in range(n):
            pre[fa[i]].append(i)
            cnt[fa[i]] += 1
        
        # 求最大的環
        vis = [False] * n
        q = deque()
        for i in range(n):
            if cnt[i] == 0:
                q.append(i)
        while q:
            cur = q.popleft()
            vis[cur] = True
            cnt[fa[cur]] -= 1
            if cnt[fa[cur]] == 0:
                q.append(fa[cur])
        
        res = 0
        def dfs(x, cnt):
            if not vis[x]:
                vis[x] = True
                dfs(fa[x], cnt + 1)
            else: 
                nonlocal res
                res = max(res, cnt)
        for i in range(n):
            if not vis[i]:
                dfs(i, 0)
                

        # 求互相喜歡的人連帶著喜歡他們的人        
        res2 = 0
        def dfs2(x, y):
            res = 0
            for i in pre[x]:
                if i != y:
                    res = max(res, dfs2(i, y))
            return res + 1
        for i in range(n):
            if fa[fa[i]] == i and fa[i] > i:
                res2 += dfs2(i, fa[i]) + dfs2(fa[i], i)
    
        print(res, res2)
        return max(res, res2)

每日一題,挺有意思的數學題

390. 消除遊戲

class Solution:
    def lastRemaining(self, n: int) -> int:
        # 1 2 3 4 5 6 
        #   3   2   1  => f(2k) = 2k + 2 - 2f(k)
        # 1 2 3 4 5 6 7
        #   3   2   1  => f(2k + 1) = 2k + 2 - 2f(k)
        return 1 if n == 1 else 2 * (n // 2 + 1- self.lastRemaining(n // 2)) 

三道劍指

劍指 Offer 06. 從尾到頭列印連結串列

# Definition for singly-linked list.
# class ListNode:
#     def __init__(self, x):
#         self.val = x
#         self.next = None

class Solution:
    def reversePrint(self, head: ListNode) -> List[int]:
        if not head: return []
        return self.reversePrint(head.next) + [head.val]

劍指 Offer 24. 反轉連結串列

# Definition for singly-linked list.
# class ListNode:
#     def __init__(self, x):
#         self.val = x
#         self.next = None

class Solution:
    def reverseList(self, head: ListNode) -> ListNode:
        cur = head
        pre = None
        while cur:
            nxt = cur.next
            cur.next = pre
            pre = cur
            cur = nxt
        return pre

劍指 Offer 35. 複雜連結串列的複製

class Solution:
    def copyRandomList(self, head: 'Node') -> 'Node':
        if not head:
            return None
        cur = head
        # 插入新節點
        while cur:
            nxt = cur.next
            cur.next = Node(cur.val, nxt, cur.random)
            cur = nxt
        cur = head.next            
        # 更新新節點的random
        while cur:
            cur.random = cur.random.next if cur.random else None
            cur = cur.next.next if cur.next else None
        cur = head
        # 拆分連結串列
        res = head.next
        while cur:
            nxt = cur.next.next
            cur.next.next = nxt.next if nxt else None
            cur.next = nxt
            cur = nxt
        return res

面試題:為什麼redis這麼快?

1、完全基於記憶體,絕大部分請求是純粹的記憶體操作,非常快速。資料存在記憶體中,類似於HashMap,HashMap的優勢就是查詢和操作的時間複雜度都是O(1);

2、資料結構簡單,對資料操作也簡單,Redis中的資料結構是專門進行設計的;

3、採用單執行緒,避免了不必要的上下文切換和競爭條件,也不存在多程序或者多執行緒導致的切換而消耗 CPU,不用去考慮各種鎖的問題,不存在加鎖釋放鎖操作,沒有因為可能出現死鎖而導致的效能消耗;

4、使用多路I/O複用模型,非阻塞IO;

5、使用底層模型不同,它們之間底層實現方式以及與客戶端之間通訊的應用協議不一樣,Redis直接自己構建了VM 機制 ,因為一般的系統呼叫系統函式的話,會浪費一定的時間去移動和請求;
連結:https://juejin.cn/post/6844903663224225806