算法题笔记
前期没有练过算法和优化方面的题,所以笔试的时候,做的特别不好,只有第一道题是最简单的。
1.得到的最少硬币数
货币系统包括1、4、16、64元共计4种硬币,以及面值为1024的纸币。现在使用1024的纸币购买一件价值为N(0<N<=1024)的商品,问最少收到多少硬币。
解:
最笨的办法就是(1024-N)/64得到的余数再除以16得到余数再除以4得到余数相加。
class Solution:
def minnum(self, N):
num = 0
res = 1024-N
for i in [64, 16, 4, 1]:
num += res/i
res = res%i
return num
f = Solution()
N = 200
a = f.minnum(N)
print a
17
3.最少奖品数
有N个人参加比赛,每个人比赛结束后都会得到一个分数,现在将N个人排成一圈领取奖品,要求:
如果某个人的分数比左右的人稿,那么奖品书一定要比左右人的多。
每个人至少得到一个奖品。
问最少应该准备多少奖品?
解:左右遍历,判断奖品数。需要注意的一点是:**N个人围成一个圈。**所以首尾需要判断。
import numpy as np
class Solution:
def minnum(self, data):
n = len(data)
m = min(data)
loc = data.index(m)
res = 0
#初始化奖品数,保证每个人都有一个奖品
num1 = [i for i in range(n)]
num2 = [i for i in range(n)]
#向右遍历
for i in range(loc+1, n):
if data[i] > data[i-1]:
num1[i] = num1[i-1]+1
if data[0] > data[n-1]:
num1[0] = num1[i]
for i in range(1, loc):
if data[i] > data[i-1]:
num1[i] = num1[i-1]+1
#向左遍历
for j in range(loc, 0, -1):
if data[j-1] > data[j]:
num2[j-1] = num2[j]+1
if data[n-1] > data[0]:
num2[n-1] = num2[0] + 1
for j in range(n-1, loc, -1):
if data[j-1] > data[j]:
num2[j-1] = num2[j]
print num1
print num2
for k in range(n):
res += max(num1[k], num2[k])
return int(res)
data = [1, 2]
f = Solution()
res = f.minnum(data)
data = [1, 2, 3, 1]
f = Solution()
res = f.minnum(data)
print res
data = [1, 0, 2]
f = Solution()
res = f.minnum(data)
print res
data = [1, 2, 2]
f = Solution()
res = f.minnum(data)
print res
相似题目Leetcode的题135——分发糖果
描述:
There are N children standing in a line. Each child is assigned a rating value.
You are giving candies to these children subjected to the following requirements:
Each child must have at least one candy.
Children with a higher rating get more candies than their neighbors.
What is the minimum candies you must give?
解:需要注意的一点是排成一列。所以向左向右判断一遍即可
class Solution(object):
def candy(self, ratings):
"""
:type ratings: List[int]
:rtype: int
"""
n = len(ratings)
num1 = [1 for i in range(n)]
num2 = [1 for i in range(n)]
res = 0
for i in range(1,n):
if ratings[i] > ratings[i-1]:
num1[i] = num1[i-1]+1
for j in range(n-1, 0, -1):
if ratings[j-1] > ratings[j]:
num2[j-1] = num2[j]+1
for i in range(n):
res += max(num1[i], num2[i])
return res
data = [1,2,87,87,87,2,1]
f = Solution()
res = f.candy(data)
print res
13
4.M根绳子最长长度
有N根绳子,第i根绳子的长度为Li,现在需要M根等长的绳子,可以对N根绳子进行任意裁剪但不能拼接,那么这M根绳子的最长长度是多少。
解:
二分法,逼近求解区间得到最优解
class Solution:
def maxlength(self, data):
N = data[0][0]
M = data[0][1]
L = data[1]
max_length = float(max(L))
min_length = 0.0
while(abs(max_length - min_length) >= 1e-3):
mid = min_length + float(max_length - min_length)/2.0
num = 0
for i in range(N):
num += int(L[i]/mid)
if num >= M:
min_length = mid
res = mid
else:
max_length = mid
return res
data中data[0]表示绳子的个数N和需要绳子个数M
data[1]表示N根绳子的长度;
f = Solution()
a = f.maxlength(data)
data=[[3, 4], [3, 5, 4]]
a = f.maxlength(data)
a
Out[16]: 2.5
data = [[3, 6], [5, 2, 3]]
a = f.maxlength(data)
a
Out[19]: 1.4996337890625
data = [[4, 5], [1, 2, 3, 4]]
a = f.maxlength(data)
a
Out[22]: 1.5