算法面试题汇总(更新中)

1、根据数字返回相应位置数字 

def get_digit(num, i):
    # i=0 个位 1 十位 2 百位...
    return num // (10 ** i) % 10

# print(get_digit(12345, 6))

2、列表反转,不用内置函数

def reverse_list(li):
    n = len(li)
    for i in range(n // 2):
        li[i], li[n-i-1] = li[n-i-1], li[i]
    return li

# print(reverse_list([1,2,3,4,5,6]))

 3、数字反转,不用切片,不用内置函数

# 123->321 12300->321
def reverse_int(num):
    is_neg = False
    if num < 0:
        is_neg = True
        num = -1 * num
    res = 0
    while num > 0:
        res = res * 10
        res += num % 10
        num = num // 10
    if is_neg:
        res = res * -1
    return res

# print(reverse_int(-123001))

4、数字转列表

def int2list(num):
    li = []
    while num > 0:
        li.append(num % 10)
        num = num // 10
    li.reverse()
    return li

# print(int2list(123456))

5、一段n个台阶组成的楼梯,小明从楼梯的最底层向最高层处前进,他可以一次迈一阶或两阶,问:他有多少种不同的走法?

def func(n):
    if n==0 or n==1:
        return 1
    else:
        return f(n-1)+f(n-2)

6、按照单词反转给定句子。例如,输入"what is your name",返回"name your is what"。请不要使用诸如''.split, [::-1]等时间/空间复杂度不是O(1)的函数

def str_reverse(str,i,j):
    while i<j:
        str[i],str[j]=str[j],str[i]
        i+=1
        j-=1
def sentence_reverse(sentence):
    sent_list = list(sentence)
    i=0
    len_list = len(sent_list)
    while i<len_list:
        if sent_list[i] !=' ':
            start = i
            end=start+1
            while (end<len_list) and (sent_list[end]!=' '):
                end += 1
            str_reverse(sent_list,start,end-1)
            i = end
        else:
            i+=1
    sent_list.reverse()
    return(''.join(sent_list))

栈,队列相关

括号匹配问题:给一个字符串,其中包含小括号、中括号、大括号,求该字符串中的括号是否匹配

def brace_match(s):
    stack = []
    d = {'(':')', '[':']', '{':'}'}
    for ch in s:
        if ch in {'(', '[', '{'}:
            stack.append(ch)
        elif len(stack) == 0:
            print('多了右括号%s' % ch)
            return False
        elif d[stack[-1]] == ch:
            stack.pop()
        else:
            print('括号%s处不匹配' % ch)
            return False
    if len(stack) == 0:
        return True
    else:
        print("剩余左括号未匹配")
        return False


print(brace_match('[]{{}[]{()})}'))

用两个栈实现队列

class QueueStack(object):
    def __init__(self):
        self.l1 = []
        self.l2 = []

    def push(self,a):
        self.l1.append(a)

    def pop(self):
        if not self.l2:
            for i in range(len(self.l1)):
                a = self.l1.pop()
                self.l2.append(a)
        if self.l2:
            return self.l2.pop()
        else:
            return False

一行代码模拟 Linux 中的 tail

# import queue # 不能设置大小
from collections import deque

# q = deque()  # 双向队列,可以设置大小,超过大小,后进队的数据会使前进队的数据被丢掉
# q.append(1)
# q.append(2)
# q.append(3)
# print(q.popleft())
# head tail

# print(deque(open('test.txt', 'r', encoding='utf-8'), 5))

 给两个字符串st,判断t是否为s的重新排列后组成的单词:

  • ns = "anagram", t = "nagaram", return true.
  • ns = "rat", t = "car", return false.
class Solution:
    def isAnagram(self, s, t):
        dict1 = {}   # 用字典来维护字符的数量
        dict2 = {}
        for ch in s:
            dict1[ch] = dict1.get(ch, 0) + 1   # 没有就新建,有就加1
        for ch in t:
            dict2[ch] = dict2.get(ch, 0) + 1
        return dict1 == dict2
 
"""
输入:"anagram","nagaram"
输出:true
Runtime: 32 ms
"""

给定一个m*n的二维列表,查找一个数是否存在。

  列表有下列特性:

  • 每一行的列表从左到右已经排序好。
  • 每一行第一个数比上一行最后一个数大。
  • leetcode地址:https://leetcode.com/problems/search-a-2d-matrix/description/

  

class Solution:
    def searchMatrix(self, matrix, target):
        h = len(matrix)  # 高
        if h == 0:
            return False
         
        w = len(matrix[0])  # 列
        if w == 0:
            return False
         
        left = 0
        right = w * h - 1
         
        while left  <= right:
            mid = ((left + right)) // 2
            i = mid // w
            j = mid % w  
            if matrix[i][j] == target:
                return True
            elif matrix[i][j] > target:
                right = mid - 1
            else:
                left = mid + 1
        else:
            return False

给定一个列表和一个整数,设计算法找到两个数的下标,使得两个数之和为给定的整数。保证肯定仅有一个结果。

  • leetcode地址:https://leetcode.com/problems/two-sum-ii-input-array-is-sorted/description/
  • 例如,列表[1,2,5,4]与目标整数3,1+2=3,结果为(0,1).
# [2,1,3,5] 4
# 第一种:循环 O(n^2)
def two_sum_1(li, num):
    for i in range(len(li)):
        for j in range(len(li)):
            if i != j:
                if li[i] + li[j] == num:
                    return i, j
    return -1,-1

# 循环减半O(n^2)
def two_sum_1_1(li, num):
    for i in range(len(li)):
        for j in range(i+1, len(li)):
            if li[i] + li[j] == num:
                return i, j


def bin_search(li, val, low, high):
    while low <= high:  # 只要候选区不空,继续循环
        mid = (low + high) // 2
        if li[mid] == val:
            return mid
        elif li[mid] < val:
            low = mid + 1
        else:  # li[mid] > val
            high = mid - 1
    return -1

# 第二种:固定一个,查找一个,查找用二分,要求有序 O(nlogn)
def two_sum_2(li, num):
    for i in range(len(li)):
        a = li[i]
        b = num - a
        j = bin_search(li, b, i+1, len(li)-1)
        if j >= 0:
            return i, j

# 第三种:左右互搏,要求有序 O(n)
def two_sum_3(li, num):
    i = 0
    j = len(li)-1
    while i < j:
        s = li[i] + li[j]
        if s == num:
            return i, j
        elif s < num:
            i += 1
        elif s > num:
            j -= 1
    return -1,-1


# 第四种:用字典,字典是O(1),不要求有序 O(n)
def two_sum_4(li, num):
    dic = {}
    for i in range(len(li)):
        a = li[i]
        b = num - li[i]
        if b not in dic:
            dic[a] = i
        else:
            return dic[b], i


# 2-sum问题
# 无序列表: 4哈希表(最优)
# 有序列表: 3两边找(最优)


# 3-sum问题
# 1.暴力枚举法 O(n^3)
# 2.二分查找   O(n^2logn)
# 3.两边找     O(n^2) (最优,不占空间)
# 4.哈希表     O(n^2) (次优)

# 2-sub问题
# 哈希表    O(n) 定住一个找两个

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值