Leetcode 455~461题

第四百五十五题:

class Solution {
public:
    int findContentChildren(vector<int>& g, vector<int>& s) {
        sort(g.begin(), g.end());
        sort(s.begin(), s.end());
        int res = 0;
        for (int i = 0, j = 0; i < g.size(); i ++ ) {
            while (j < s.size() && s[j] < g[i]) j ++ ;
            if (j < s.size()) {
                res ++ ;
                j ++ ;
            }
            else break;
        }
        return res;
    }
};
class Solution {
    public int findContentChildren(int[] g, int[] s) {
        Arrays.sort(g);
        Arrays.sort(s);
        int numOfChildren = g.length, numOfCookies = s.length;
        int count = 0;
        for (int i = 0, j = 0; i < numOfChildren && j < numOfCookies; i++, j++) {
            while (j < numOfCookies && g[i] > s[j]) {
                j++;
            }
            if (j < numOfCookies) {
                count++;
            }
        }
        return count;
    }
}
class Solution:
    def findContentChildren(self, g: List[int], s: List[int]) -> int:
        g.sort()
        s.sort()
        n, m = len(g), len(s)
        i = j = count = 0

        while i < n and j < m:
            while j < m and g[i] > s[j]:
                j += 1
            if j < m:
                count += 1
            i += 1
            j += 1
        
        return count
func findContentChildren(greed, size []int) (ans int) {
    sort.Ints(greed)
    sort.Ints(size)
    n, m := len(greed), len(size)
    for i, j := 0, 0; i < n && j < m; i++ {
        for j < m && greed[i] > size[j] {
            j++
        }
        if j < m {
            ans++
            j++
        }
    }
    return
}

第四百五十六题:

class Solution {
public:
    bool find132pattern(vector<int>& nums) {
        stack<int> stk;
        int right = INT_MIN;
        for (int i = nums.size() - 1; i >= 0; i -- ) {
            if (nums[i] < right) return true;
            while (stk.size() && nums[i] > stk.top()) {
                right = max(right, stk.top());
                stk.pop();
            }
            stk.push(nums[i]);
        }
        return false;
    }
};
class Solution {
    public boolean find132pattern(int[] nums) {
        int n = nums.length;
        List<Integer> candidateI = new ArrayList<Integer>();
        candidateI.add(nums[0]);
        List<Integer> candidateJ = new ArrayList<Integer>();
        candidateJ.add(nums[0]);

        for (int k = 1; k < n; ++k) {
            int idxI = binarySearchFirst(candidateI, nums[k]);
            int idxJ = binarySearchLast(candidateJ, nums[k]);
            if (idxI >= 0 && idxJ >= 0) {
                if (idxI <= idxJ) {
                    return true;
                }
            }
            
            if (nums[k] < candidateI.get(candidateI.size() - 1)) {
                candidateI.add(nums[k]);
                candidateJ.add(nums[k]);
            } else if (nums[k] > candidateJ.get(candidateJ.size() - 1)) {
                int lastI = candidateI.get(candidateI.size() - 1);
                while (!candidateJ.isEmpty() && nums[k] > candidateJ.get(candidateJ.size() - 1)) {
                    candidateI.remove(candidateI.size() - 1);
                    candidateJ.remove(candidateJ.size() - 1);
                }
                candidateI.add(lastI);
                candidateJ.add(nums[k]);
            }
        }

        return false;
    }

    public int binarySearchFirst(List<Integer> candidate, int target) {
        int low = 0, high = candidate.size() - 1;
        if (candidate.get(high) >= target) {
            return -1;
        }
        while (low < high) {
            int mid = (high - low) / 2 + low;
            int num = candidate.get(mid);
            if (num >= target) {
                low = mid + 1;
            } else {
                high = mid;
            }
        }
        return low;
    }

    public int binarySearchLast(List<Integer> candidate, int target) {
        int low = 0, high = candidate.size() - 1;
        if (candidate.get(low) <= target) {
            return -1;
        }
        while (low < high) {
            int mid = (high - low + 1) / 2 + low;
            int num = candidate.get(mid);
            if (num <= target) {
                high = mid - 1;
            } else {
                low = mid;
            }
        }
        return low;
    }
}
class Solution:
    def find132pattern(self, nums: List[int]) -> bool:
        candidate_i, candidate_j = [-nums[0]], [-nums[0]]

        for v in nums[1:]:
            idx_i = bisect.bisect_right(candidate_i, -v)
            idx_j = bisect.bisect_left(candidate_j, -v)
            if idx_i < idx_j:
                return True

            if v < -candidate_i[-1]:
                candidate_i.append(-v)
                candidate_j.append(-v)
            elif v > -candidate_j[-1]:
                last_i = -candidate_i[-1]
                while candidate_j and v > -candidate_j[-1]:
                    candidate_i.pop()
                    candidate_j.pop()
                candidate_i.append(-last_i)
                candidate_j.append(-v)

        return False
func find132pattern(nums []int) bool {
    candidateI, candidateJ := []int{-nums[0]}, []int{-nums[0]}

    for _, v := range nums[1:] {
        idxI := sort.SearchInts(candidateI, 1-v)
        idxJ := sort.SearchInts(candidateJ, -v)
        if idxI < idxJ {
            return true
        }

        if v < -candidateI[len(candidateI)-1] {
            candidateI = append(candidateI, -v)
            candidateJ = append(candidateJ, -v)
        } else if v > -candidateJ[len(candidateJ)-1] {
            lastI := -candidateI[len(candidateI)-1]
            for len(candidateJ) > 0 && v > -candidateJ[len(candidateJ)-1] {
                candidateI = candidateI[:len(candidateI)-1]
                candidateJ = candidateJ[:len(candidateJ)-1]
            }
            candidateI = append(candidateI, -lastI)
            candidateJ = append(candidateJ, -v)
        }
    }

    return false
}

第四百五十七题:

class Solution {
public:
    bool circularArrayLoop(vector<int>& nums) {
        int n = nums.size(), Base = 10000;
        for (int i = 0; i < n; i ++ ) {
            if (nums[i] >= Base) continue;
            int k = i, S = Base + i, t = nums[k] > 0;
            int last = -1;
            do {
                int p = ((k + nums[k]) % n + n) % n;
                last = nums[k], nums[k] = S;
                k = p;
            } while (k != i && nums[k] < Base && (t ^ (nums[k] > 0)) == 0);
            if (last % n && nums[k] == S) return true;
        }
        return false;
    }
};
private void setZero(int[] nums, int i){
        int j;
        while (true) { // !(nums[j] == 0 || nums[i]*nums[j]<0)
            j = (i + nums[i] + 5000*nums.length) % nums.length;
            if (nums[j] == 0 || nums[i]*nums[j]<0) {
                nums[i] = 0;
                break;
            }
            nums[i] = 0;
            i = j;
        }
    }

    // beat 100%
    public boolean circularArrayLoop(int[] nums) {
        if (nums.length == 0) return false;
        for (int i = 0; i < nums.length; i++) {
            if (nums[i] == 0) continue;
            int lastJ, lastK;
            int j=i, k=i;

            while (true) {
                lastJ = j;
                j = (j + nums[j] + 5000*nums.length) % nums.length;
                if (nums[lastJ]*nums[j] < 0 || nums[j] == 0 || lastJ == j) {
                    setZero(nums, i);
                    break;
                }
                lastK = k;
                k = (k + nums[k] + 5000*nums.length) % nums.length;
                if (nums[lastK]*nums[k] < 0 || nums[k] == 0 || lastK == k){
                    setZero(nums, i);
                    break;
                }
                lastK = k;
                k = (k + nums[k] + 5000*nums.length) % nums.length;
                if (nums[lastK]*nums[k] < 0 || nums[k] == 0 || lastK == k){
                    setZero(nums, i);
                    break;
                }
                if (j == k)
                    return true;
            }
        }
        return false;
    }
class Solution:
    def circularArrayLoop(self, nums: List[int]) -> bool:
        n = len(nums)
        # x的下一个位置
        nxt = lambda x: (x + nums[x]) % n

        for i in range(n):
            if nums[i] == 0: continue
            slow = i
            fast = nxt(i)
            # 快慢指针
            """符号相同保证是同一个方向移动"""
            while nums[slow] * nums[fast] > 0 and nums[fast] * nums[nxt(fast)] > 0:
                """快指针每次走两步,如果快慢指针相等,说明有环"""
                if slow == fast:
                    """如果是自身环,那么退出循环"""
                    if slow == nxt(slow):
                        break
                    else:
                        return True
                """更新状态,快指针每次走两步"""
                slow = nxt(slow)
                fast = nxt(nxt(fast))
            # 访问过的置0
            """如果上面那轮没有return,说明上面遍历过的元素都不可能成环,为避免再次遍历陷入无效查找,故将查找过的元素置零,再次遍历时直接跳过"""
            while nums[i] > 0:
                """先找到下一个元素的index"""
                tmp = nxt(i)
                """将当前的元素置零"""
                nums[i] = 0
                """向下走一步"""
                i = tmp
        return False
func circularArrayLoop(nums []int) bool {
    epcho := 10001
    length := len(nums)
    isPositive := true
    for index,num := range nums {
        if num > 0 {
            isPositive = true
        } else {
            isPositive = false
        }
        for true {
            if num == epcho {
                return true
            } else if num > 1000 {
                break;
            } else if (isPositive && (num < 0)) || (!isPositive && num>0) {
                break;
            } else {
                nums[index] = epcho
                nextIndex := (num + index)%length
                if nextIndex < 0 {
                    nextIndex = nextIndex+length
                }
                if index == nextIndex {
                    break;
                }
                index = nextIndex
                num = nums[index]
            }
        }
        epcho ++
    }

    return false
}

第四百五十八题:

class Solution {
public:
    int poorPigs(int n, int minutesToDie, int minutesToTest) {
        int k = minutesToTest / minutesToDie;
        return ceil(log(n) / log(k + 1));
    }
};
class Solution {
public:
    int poorPigs(int n, int minutesToDie, int minutesToTest) {
        int k = minutesToTest / minutesToDie;
        return ceil(log(n) / log(k + 1));
    }
};
class Solution:
    def poorPigs(self, buckets: int, minutesToDie: int, minutesToTest: int) -> int:
        states = minutesToTest // minutesToDie + 1
        return math.ceil(math.log(buckets) / math.log(states))
func poorPigs(buckets int, minutesToDie int, minutesToTest int) int {
    times := minutesToTest/minutesToDie
    times = times + 1
    result := math.Log(float64(buckets))/math.Log(float64(times))
    return int(math.Ceil(result))
}

第四百五十九题:

class Solution {
public:
    bool repeatedSubstringPattern(string s) {
        int n = s.size();
        s = ' ' + s;
        vector<int> next(n + 1);
        for (int i = 2, j = 0; i <= n; i ++ ) {
            while (j && s[i] != s[j + 1]) j = next[j];
            if (s[i] == s[j + 1]) j ++ ;
            next[i] = j;
        }
        int t = n - next[n];
        return t < n && n % t == 0;
    }
};
class Solution {
    public boolean repeatedSubstringPattern(String s) {
        return kmp(s);
    }

    public boolean kmp(String pattern) {
        int n = pattern.length();
        int[] fail = new int[n];
        Arrays.fill(fail, -1);
        for (int i = 1; i < n; ++i) {
            int j = fail[i - 1];
            while (j != -1 && pattern.charAt(j + 1) != pattern.charAt(i)) {
                j = fail[j];
            }
            if (pattern.charAt(j + 1) == pattern.charAt(i)) {
                fail[i] = j + 1;
            }
        }
        return fail[n - 1] != -1 && n % (n - fail[n - 1] - 1) == 0;
    }
}
class Solution:
    def repeatedSubstringPattern(self, s: str) -> bool:
        def kmp(pattern: str) -> bool:
            n = len(pattern)
            fail = [-1] * n
            for i in range(1, n):
                j = fail[i - 1]
                while j != -1 and pattern[j + 1] != pattern[i]:
                    j = fail[j]
                if pattern[j + 1] == pattern[i]:
                    fail[i] = j + 1
            return fail[n - 1] != -1 and n % (n - fail[n - 1] - 1) == 0
        
        return kmp(s)
func repeatedSubstringPattern(s string) bool {
    return kmp(s)
}

func kmp(pattern string) bool {
    n := len(pattern)
    fail := make([]int, n)
    for i := 0; i < n; i++ {
        fail[i] = -1
    }
    for i := 1; i < n; i++ {
        j := fail[i - 1]
        for (j != -1 && pattern[j + 1] != pattern[i]) {
            j = fail[j]
        }
        if pattern[j + 1] == pattern[i] {
            fail[i] = j + 1
        }
    }
    return fail[n - 1] != -1 && n % (n - fail[n - 1] - 1) == 0
}

第四百六十题:

class LFUCache {
public:
    struct Node {
        Node *left, *right;
        int key, val;
        Node(int _key, int _val) {
            key = _key, val = _val;
            left = right = NULL;
        }
    };
    struct Block {
        Block *left, *right;
        Node *head, *tail;
        int cnt;
        Block(int _cnt) {
            cnt = _cnt;
            left = right = NULL;
            head = new Node(-1, -1), tail = new Node(-1, -1);
            head->right = tail, tail->left = head;
        }
        ~Block() {
            delete head;
            delete tail;
        }
        void insert(Node* p) {
            p->right = head->right;
            head->right->left = p;
            p->left = head;
            head->right = p;
        }
        void remove(Node* p) {
            p->left->right = p->right;
            p->right->left = p->left;
        }
        bool empty() {
            return head->right == tail;
        }
    }*head, *tail;
    int n;
    unordered_map<int, Block*> hash_block;
    unordered_map<int, Node*> hash_node;

    void insert(Block* p) {  // 在p的右侧插入新块,cnt是p->cnt + 1
        auto cur = new Block(p->cnt + 1);
        cur->right = p->right;
        p->right->left = cur;
        p->right = cur;
        cur->left = p;
    }

    void remove(Block* p) {
        p->left->right = p->right;
        p->right->left = p->left;
        delete p;
    }

    LFUCache(int capacity) {
        n = capacity;
        head = new Block(0), tail = new Block(INT_MAX);
        head->right = tail, tail->left = head;
    }

    int get(int key) {
        if (hash_block.count(key) == 0) return -1;
        auto block = hash_block[key];
        auto node = hash_node[key];
        block->remove(node);
        if (block->right->cnt != block->cnt + 1) insert(block);
        block->right->insert(node);
        hash_block[key] = block->right;
        if (block->empty()) remove(block);
        return node->val;
    }

    void put(int key, int value) {
        if (!n) return;
        if (hash_block.count(key)) {
            hash_node[key]->val = value;
            get(key);
        } else {
            if (hash_block.size() == n) {
                auto p = head->right->tail->left;
                head->right->remove(p);
                if (head->right->empty()) remove(head->right);
                hash_block.erase(p->key);
                hash_node.erase(p->key);
                delete p;
            }
            auto p = new Node(key, value);
            if (head->right->cnt > 1) insert(head);
            head->right->insert(p);
            hash_block[key] = head->right;
            hash_node[key] = p;
        }
    }
};

/**
 * Your LFUCache object will be instantiated and called as such:
 * LFUCache* obj = new LFUCache(capacity);
 * int param_1 = obj->get(key);
 * obj->put(key,value);
 */
class LFUCache {
    // 缓存容量,时间戳
    int capacity, time;
    Map<Integer, Node> key_table;
    TreeSet<Node> S;

    public LFUCache(int capacity) {
        this.capacity = capacity;
        this.time = 0;
        key_table = new HashMap<Integer, Node>();
        S = new TreeSet<Node>();
    }
    
    public int get(int key) {
        if (capacity == 0) {
            return -1;
        }
        // 如果哈希表中没有键 key,返回 -1
        if (!key_table.containsKey(key)) {
            return -1;
        }
        // 从哈希表中得到旧的缓存
        Node cache = key_table.get(key);
        // 从平衡二叉树中删除旧的缓存
        S.remove(cache);
        // 将旧缓存更新
        cache.cnt += 1;
        cache.time = ++time;
        // 将新缓存重新放入哈希表和平衡二叉树中
        S.add(cache);
        key_table.put(key, cache);
        return cache.value;
    }
    
    public void put(int key, int value) {
        if (capacity == 0) {
            return;
        }
        if (!key_table.containsKey(key)) {
            // 如果到达缓存容量上限
            if (key_table.size() == capacity) {
                // 从哈希表和平衡二叉树中删除最近最少使用的缓存
                key_table.remove(S.first().key);
                S.remove(S.first());
            }
            // 创建新的缓存
            Node cache = new Node(1, ++time, key, value);
            // 将新缓存放入哈希表和平衡二叉树中
            key_table.put(key, cache);
            S.add(cache);
        } else {
            // 这里和 get() 函数类似
            Node cache = key_table.get(key);
            S.remove(cache);
            cache.cnt += 1;
            cache.time = ++time;
            cache.value = value;
            S.add(cache);
            key_table.put(key, cache);
        }
    }
}

class Node implements Comparable<Node> {
    int cnt, time, key, value;

    Node(int cnt, int time, int key, int value) {
        this.cnt = cnt;
        this.time = time;
        this.key = key;
        this.value = value;
    }

    public boolean equals(Object anObject) {
        if (this == anObject) {
            return true;
        }
        if (anObject instanceof Node) {
            Node rhs = (Node) anObject;
            return this.cnt == rhs.cnt && this.time == rhs.time;
        }
        return false;
    }

    public int compareTo(Node rhs) {
        return cnt == rhs.cnt ? time - rhs.time : cnt - rhs.cnt;
    }

    public int hashCode() {
        return cnt * 1000000007 + time;
    }
}
class Node:
    def __init__(self, key=None, value=None):
        self.key = key
        self.val = value
        self.freq = 1
        self.next = None
        self.pre = None

class Dlink:
    def __init__(self):
        self.head = Node()
        self.tail = Node()
        self.head.next = self.tail
        self.tail.pre = self.head
        self.size = 0

    def _append(self, node):
        self.tail.pre.next = node
        node.pre = self.tail.pre
        node.next = self.tail
        self.tail.pre = node
        self.size += 1

    
    def _pop_node(self,node=None):
        if not node:
            node = self.head.next
            self.head.next = node.next
            node.next.pre = self.head
        else:
            node.pre.next = node.next
            node.next.pre = node.pre
        self.size -= 1
        return node


class LFUCache:

    def __init__(self, capacity: int):
        self.capacity = capacity
        self.key_node = {}   # {key:node, ...}
        self.freq = {}       # {key:dlink, ...}
        self.min_freq = 0

    def get(self, key: int) -> int:
        if key in self.key_node:
            node = self.key_node[key]
            self.increase_freq_key(key)
            return node.val
        return -1

    def put(self, key: int, value: int) -> None:
        if self.capacity == 0:
            return
        elif key in self.key_node:
            self.key_node[key].val = value
            self.increase_freq_key(key)
        else:
            if len(self.key_node) >= self.capacity:
                self.remove_minfreq_key()
            if 1 not in self.freq:
                self.freq[1] = Dlink()
            node = Node(key, value)
            self.key_node[key] = node
            self.freq[1]._append(node)
            self.min_freq = 1

    def increase_freq_key(self, key):
        """key,freq已经存在"""
        node = self.key_node[key]
        node_freq = node.freq
        self.freq[node_freq]._pop_node(node)
        if self.min_freq == node_freq and self.freq[node_freq].size == 0:
            self.min_freq += 1
        node.freq += 1
        if node.freq not in self.freq:
            self.freq[node.freq] = Dlink()
        self.freq[node.freq]._append(node)
        self.key_node[key] = node
            
    def remove_minfreq_key(self):
        node = self.freq[self.min_freq]._pop_node()
        del self.key_node[node.key]

# Your LFUCache object will be instantiated and called as such:
# obj = LFUCache(capacity)
# param_1 = obj.get(key)
# obj.put(key,value)
type LFUCache struct {
  cache map[int]*Node
  freq map[int]*DoubleList
  ncap, size, minFreq int
}

func Constructor(capacity int) LFUCache {
  return LFUCache {
    cache: make(map[int]*Node),
    freq: make(map[int]*DoubleList),
    ncap: capacity,
  }
}

func (this *LFUCache) Get(key int) int {
  if node, ok := this.cache[key]; ok {
    this.IncFreq(node)
    return node.val
  }
  return -1
}

func (this *LFUCache) Put(key, value int) {
  if this.ncap == 0 {
    return
  }
  if node, ok := this.cache[key]; ok {
    node.val = value
    this.IncFreq(node)
  } else {
    if this.size >= this.ncap {
      node := this.freq[this.minFreq].RemoveLast()
      delete(this.cache, node.key)
      this.size--
    }
    x := &Node{key: key, val: value, freq: 1}
    this.cache[key] = x
    if this.freq[1] == nil {
      this.freq[1] = CreateDL()
    }
    this.freq[1].AddFirst(x)
    this.minFreq = 1
    this.size++
  }
}

func (this *LFUCache) IncFreq(node *Node) {
  _freq := node.freq
  this.freq[_freq].Remove(node)
  if this.minFreq == _freq && this.freq[_freq].IsEmpty() {
    this.minFreq++
    delete(this.freq, _freq)
  }

  node.freq++
  if this.freq[node.freq] == nil {
    this.freq[node.freq] = CreateDL()
  }
  this.freq[node.freq].AddFirst(node)
}

type DoubleList struct {
  head, tail *Node
}

type Node struct {
  prev, next *Node
  key, val, freq int
}

func CreateDL() *DoubleList {
  head, tail := &Node{}, &Node{}
  head.next, tail.prev = tail, head
  return &DoubleList {
    head: head,
    tail: tail,
  }
}

func (this *DoubleList) AddFirst(node *Node) {
  node.next = this.head.next
  node.prev = this.head

  this.head.next.prev = node
  this.head.next = node
}

func (this *DoubleList) Remove(node *Node) {
  node.prev.next = node.next
  node.next.prev = node.prev

  node.next = nil
  node.prev = nil
}

func (this *DoubleList) RemoveLast() *Node {
  if this.IsEmpty() {
    return nil
  }

  last := this.tail.prev
  this.Remove(last)

  return last
}

func (this *DoubleList) IsEmpty() bool {
  return this.head.next == this.tail
}

/**
 * Your LFUCache object will be instantiated and called as such:
 * obj := Constructor(capacity);
 * param_1 := obj.Get(key);
 * obj.Put(key,value);
 */

第四百六十一题:

class Solution {
public:
    int hammingDistance(int x, int y) {
        int res = 0;
        while (x || y) {
            res += (x & 1) ^ (y & 1);
            x >>= 1, y >>= 1;
        }
        return res;
    }
};
class Solution {
    public int hammingDistance(int x, int y) {
        return Integer.bitCount(x ^ y); 
    }
}
class Solution:
    def hammingDistance(self, x: int, y: int) -> int:
        return bin(x ^ y).count('1')
func hammingDistance(x int, y int) int {
    i :=x^y//x和y异或,得到一个新的数(异或相同为0,不同为1,此时咱们需要统计1的个数)
    count :=0//定义数量的初始值为0
    for(i!=0){//只要i不为0,那就继续循环
        if ((i&1)==1){//如果i和1相与,值为1的话就count++
            count++
        }
        i = i>>1//i右移一位
    }
    return count

}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

不能say的秘密

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值