💡
Seb's Whiteboard
  • 👨‍💻Welcome, I'm Sebastien St Vil
  • Extras
    • Gradient Descent
    • How I learned Java
    • Machine Learning by Andrew Ng
  • Projects
    • 📉Backtest Equity Trading with SMA Strategy
    • Wellington GA Lab
    • Stock analysis
    • 📈Time Series Regression-based Trading Strategy
  • Arrays & Strings
    • Best Time to Buy and Sell Stock II
    • Online Stock Span
    • Implement strStr()
    • 2Sum
    • 3Sum
    • 3Sum Closest
    • 4Sum II
    • Set Matrix Zeroes
    • Group Anagrams
    • Longest Substring Without Repeating Characters
    • Remove Duplicates from Sorted Array
    • Move Zeroes
    • Valid Sudoku
    • Rotate Image
    • First Unique Character in a String
    • Design a Circular Queue
    • Longest Common Prefix
  • Binary Tree
  • Second Minimum Node In a Binary Tree (671)
  • Design
  • LRU Cache
  • Min Stack (155)
  • Sorting & Searching
    • Merge Sorted Array (88)
    • First Bad Version
  • Math
    • Power of Three (326)
    • Power of Two (231)
    • Count Prime (204)
    • Roman to Integer (13)
    • Fizz Buzz (412)
    • Count-and-Say
  • Dynamic Programming
    • Pascal's Triangle (118)
  • Linked List
    • Copy List with Random Pointer
    • Remove Nth Node From End of List
    • Remove Duplicated from Sorted List II
  • Tips
    • Finding dups
  • Sliding Window
    • Subarray Product Less Than K
Powered by GitBook
On this page

Was this helpful?

LRU Cache

Implement the LRUCache class

PreviousSecond Minimum Node In a Binary Tree (671)NextMin Stack (155)

Last updated 3 years ago

Was this helpful?

class ListNode:
    def __init__(self,key=-1, value=-1, next=None, prev=None):
        self.key = key
        self.value = value
        self.next = next
        self.prev = prev

class LRUCache:
     def __init__(self, capacity: int):
        self.capacity = capacity
        self.cache = dict()
        self.head = ListNode()
        self.tail = ListNode()
        self.head.next = self.tail
        self.tail.prev = self.head

     def get(self, key: int) -> int:
        if key not in self.cache: return -1
        
        node = self.cache[key]
        v = node.value
        self.remove(node)
        self.add(node)
        return v

     def put(self, key: int, value: int) -> None:
        if key not in self.cache:
            if len(self.cache) >= self.capacity:
                self.pop_lru()
            self.add(ListNode(key,value))
        else:
            node = self.cache[key]
            node.value = value
            self.remove(node)
            self.add(node)
    
    def add(self, node:ListNode) -> None:
        self.tail.prev.next = node
        node.prev = self.tail.prev
        node.next = self.tail
        self.tail.prev = node
        self.cache[node.key] = node
    
    def remove(self, node: ListNode) -> None:
        node.prev.next = node.next
        node.next.prev = node.prev
        del self.cache[node.key]
    
    def pop_lru(self) -> None:
        self.remove(self.head.next)

Approach2: Inneficient using Queue properties

from collections import deque, namedtuple
class LRUCache:

    def __init__(self, capacity: int):
        self.deq = deque()
        self.size = capacity
        self.Pair = namedtuple('pair', ['key', 'value'])
        
    def get(self, key: int) -> int:
        index = self.find(key)
        if index == -1: return -1
        value = self.deq[index].value
        del self.deq[index]
        self.deq.append(self.Pair(key=key, value=value))
        return value
    
    def put(self, key: int, value: int) -> None:
        index = self.find(key)
        
        if index == -1:
            if len(self.deq) >= self.size:
                del self.deq[0]
        else:
            del self.deq[index]
        self.deq.append(self.Pair(key=key, value=value))
        
    def find(self, key: int) -> int:
        for index, pair in enumerate(self.deq):
            if pair.key == key:
                return index
        return -1