# Company real question brush record Python

Posted by myharshdesigner on Thu, 18 Jun 2020 06:28:06 +0200

## Greedy Algorithm

Resource allocation, maximizing revenue
Xiaoq's company recently received m tasks, the i task needs xi time to complete, and the difficulty level is yi.
Xiaoq has n machines, the longest working time of each machine is zi, and the machine level is wi.
For a task, it can only be completed by one machine. If the maximum working time of the machine assigned to it is less than the time required by the task, it cannot be completed. If the task is completed, it will gain 200 * xi + 3 * yi.

For a machine, it can only complete one task a day. If its machine level is lower than the task difficulty level assigned to it, it cannot complete.

Xiaoq wants to finish as many tasks as possible today, that is to say, the number of tasks completed is the largest. If there are multiple arrangements, xiaoq also wants to find the one with the most profit. Xiaoq needs you to help him calculate.
Enter a description:

The input includes N + M + 1 lines,
The first input line is two positive integers n and m (1 < = n, m < = 100000), indicating the number of machines and tasks.
Next n lines, each line has two integers zi and wi (0 < zi < 1000, 0 < = wi < = 100), indicating the maximum working time and machine level of each machine.
The next m lines, two integers xi and Yi (0 < xi < 1000, 0 < = Yi < = 100) in each line, indicate the completion time and difficulty level of each task.
Output Description:
Output two integers, representing the maximum number of tasks that can be completed and the revenue obtained.
Example 1
Input:
1 2
100 3
100 2
100 1
output
1 20006

#Greedy algorithm, in order to ensure the maximization of benefits, completes the most time first, so sorts machines and tasks from large to small according to time
class node():
def __init__(self,time,level):
self.time=time
self.level=level
#Read the first line of input, number of machines and number of tasks
n,m=map(int,input().split())
machines=[]
jobs=[]
#Read the maximum working time and machine level of each machine
for i in range(n):
time,level= map(int,input().split(' '))
machine = node(time,level)
machines.append(machine)
for i in range(m):
time,level= map(int,input().split(' '))
job = node(time,level)
jobs.append(machine)
#Sort by time
machines.sort(key=lambda x:(x.time,x.level),reverse=True)
jobs.sort(key=lambda x:(x.time,x.level),reverse=True)
#Revenue and number of jobs
profit=0
count=0
j=0#Until the machine runs out or does not work
levels=*101
for i in range(m):
#Two restrictions, the serial judgment condition should be used
while j<n and machines[j].time>jobs[i].time:
#Record machines that meet time conditions
levels[machines[j].level]+=1
j+=1
for k in range(jobs[i].level,101):
#A machine that judges whether there is a level of satisfaction
if(levels[k]):
count+=1
levels[k]-=1
profit+=200*jobs[i].time+3*jobs[i].level
break
print(count, end=' ')
print(profit)


## Dictionary order

Dictionary order minimum: from small to large
Dictionary order: from large to small
Source: niuke.com

One day, Xiaoyi put all the permutations from 1 to n in a dictionary order. Xiaoyi chooses a permutation from it. Suppose it is the Q permutation of positive number. Xiaoyi hopes you can answer what the Q permutation of reciprocal number is.
For example, all permutations from 1 to 3 are:
1 2 3
1 3 2
2 1 3
2 3 1
3 1 2
3 2 1
If Xiaoyi chooses 1 2 3, then Q = 1, and you should output 3 2 1
Enter a description:
The number n in the first row indicates the arrangement length
Next n numbers in a row indicate the selected arrangement
1≤n≤3000001≤n≤3000001 \leq n \leq 3000001≤n≤3000001≤n≤3000001≤n≤300000
Output Description:
A row of n numbers representing the desired arrangement
Example
Input:
3
1 2 3
output
3 2 1

#It can be seen from the analysis that the two permutations of position are relatively symmetric, and the sum of corresponding digits is n+1, so the output can be calculated directly


## Huawei test

1. Divide by a space. Only the year and day of the first group contain the day of the week. Please calculate the day of the year and the day of the second group.

a = input().split('|')
begin = list(map(int, a.split()))
end = list(map(int, a.split()))
# Count the days and divide by 7
year = end - begin
mounth = end - end
mounths = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]
weeks = [1, 2, 3, 4, 5, 6, 7]
day = [0, 0]
# Calculate the date separately as the day of this year
if ((begin % 4 == 0 and begin % 100 != 0) or begin % 400 == 0):
mounths = 29
for i in range(begin-1):
day += mounths[i]
day += begin
# Calculate the days of end in the year
if ((end % 4 == 0 and end % 100 != 0) or end % 400 == 0):
mounths = 29
else:
mounths = 28
for i in range(end-1):
day += mounths[i]
day += end
if year == 0:
days = day - day
else:
days = 0
for i in range(begin, end):
if ((i % 4 == 0 and i % 100 != 0) or i % 400 == 0):
days += 366
else:
days += 365
days = days - day + day
# Calculate leap year
# Get the difference between two dates
print(days)
result = (days % 7 + begin) % 7
if(result==0):
result=7
print(result)


2. There are several fixed position street lights on a road, which need to illuminate all bus stops on the road; now give the location serial number of all bus stops and roads on the road, and the bus stops and street lights are arranged on the road according to the location serial number.
Calculate the brightness of the street light to illuminate all the bus stops on the road,

a = list(map(int, input().split(',')))
b = list(map(int, input().split(',')))
print(a, b)
a.sort()
b.sort()
# Find the maximum of several values
minnums = []
# Calculation of intermediate position
for i in range(len(a)):
minnum = 10000
for j in range(len(b)):
if (abs(a[i] - b[j]) < minnum):
minnum = abs(a[i] - b[j])
minnums.append(minnum)
print(minnums)
result = max(minnums)
print(result)


3. The owner of the rental house plans to buy a batch of new books, selects n books with the same price as alternatives, and sends a batch of questionnaires to the vip readers. The mobile phone goes to the list of books that each reader wants to read. In order to save the purchase cost, the owner decides to make sure that each vip reader has at least one favorite book in the purchase list to minimize the purchase cost. Output the minimum number of purchased books
Input example
5
3
1 2 3 4 5
1 2
2
3 4

Prototype topic: dynamic planning + binary search
Title:
You will get K eggs and can use a building with N floors from 1 to N.

Every egg has the same function. If an egg breaks, you can't drop it.

You know that there is floor F. any egg falling from a floor higher than f will be broken, and the egg falling from a floor f or a floor lower than f will not be broken.

Each time you move, you can take an egg (if you have a complete egg) and drop it from any floor X (meet 1 < = X < = n).

Your goal is to know exactly what the value of F is.

No matter what the initial value of F is, how many times do you determine the minimum movement of the value of F?

Example:
Input: K = 1, N = 2
Output: 2
Explanation:
The eggs fell from the first floor. If it breaks, we know F = 0.
Otherwise, the eggs fall off the second floor. If it breaks, we know F = 1.
If it's not broken, then we know F = 2.
So in the worst case we need to move twice to determine what F is.
Idea: after the number of eggs and the floor are determined, the minimum number of movements will also be determined, so the number of k,n corresponding to the number of dynamic planning can be obtained.
1. There are two cases of dropping eggs from floor X: broken and not broken. If broken, the next step is f(k-1,x-1). If not broken, f(k,n-x). Therefore, the minimum number of movements needed to find the critical floor is f(k,n)=max{fx(k-1,x-1),fx(k,n-x)}
2. It is known that f(k,n) should be the minimum value of all cases, that is, f(k,n)=min{f1(),f2() fn()}
Time complexity: O(kn^2)

class Solution:
def superEggDrop(self, k: int, n: int) -> int:
def parse(k, n):
if n == 1:  # If there is only one layer, no matter how many eggs there are, just try it once
return 1
elif n == 0:
return 0
elif k == 1:  # If there is only one egg, it can only be tested layer by layer
return n
elif (k, n) in table:
return table[(k, n)]

f = float('inf')  # Define an infinite number as the initial condition
for x in range(1, n + 1):  # Drop the eggs on layer x, starting with layer 1
fx = 1 + max(parse(k - 1, x - 1), parse(k, n - x))
f = min(f, fx)

table[(k, n)] = f
return f

table = {}  # Memory is counted
return parse(k, n)



Optimization scheme: dynamic planning + binary search
The observation shows that fx(k-1,x-1) increases monotonically with the increase of X, fx(k,n-x) decreases monotonically with the increase of X, so we can find out the worst case by binary search. To find the minimum value code:

 for x in range(1, n + 1):  # Drop the eggs on layer x, starting with layer 1
fx = 1 + max(parse(k - 1, x - 1), parse(k, n - x))
f = min(f, fx)



Change to:

while lp <= rp:
mid = lp + (rp-lp) // 2  # Dichotomy optimization
bcase = parse(k-1, mid-1)  # Broken eggs
notbcase = parse(k,n-mid)  # Unbreakable situation
# fx = 1 + max(bcase, notbcase)
if bcase > notbcase:
rp = mid - 1
f = min(f, bcase + 1)
else:
lp = mid + 1
f = min(f,notbcase + 1)


## Sort + two pointer search

Daily question:
Give you a n array of N integers, nums, to determine whether there are three elements a, b, c in nums, making a + b + c = 0? Please find out all the triples that meet the conditions and do not repeat.
Idea: sort the array and traverse the benchmark number from the beginning. Use two pointers to traverse at the first place of the following number. Because the array is monotonous, the search is unidirectional.

 def threeSum(self,nums):
nums.sort()

res, k = [], 0
length = len(nums)
for k in range(length-2):

if nums[k] > 0:  # The latter are greater than 0, and the latter are greater than zero
break
if(k>0 and nums[k]==nums[k-1]):#Avoid duplicate triples. Skip the next benchmark as before
continue
i = k + 1
j = length - 1
while i < j:#Conditions for two head and tail pointers

if((nums[k] + nums[i] + nums[j] )< 0):

i += 1
elif ((nums[k] + nums[i] + nums[j]) > 0):
j -= 1
else:
a = [nums[k], nums[i], nums[j]]
res.append(a)
while i<j:
if(nums[i] == nums[i + 1] ):#Exclude the same tuple
i+=1

elif(nums[j] == nums[j - 1]):
j-=1
else:
i+=1
j-=1
break
return res


## to flash back

Given an array candidates and a target number target, find out all combinations of candidates that can make the number and target.

Each number in candidates can only be used once in each combination.

def combinationSum2(self, candidates: List[int], target: int) -> List[List[int]]:
candidates.sort()#Now the array is sorted in order to ensure the monotonicity of the search direction
self.res = []
if (target == 0 or len(candidates) == 0):
return res

def helper(tar, cur, idx):
# cur records the node of the current record, so it needs to be passed down
if (tar==0):
# Start a new search
self.res.append(cur[:])
for i in range(int(idx), len(candidates)):
if (tar < candidates[i]):
# The following number must be greater than tar. There is no target value. End directly
break
elif (i > idx and candidates[i] == candidates[i - 1]):
# Avoid duplicate nodes
continue
# The rest is that the node is smaller than the target value, save the node and carry out the next search

cur.append(candidates[i])
helper(tar - candidates[i], cur,i + 1)
cur.pop()  # Restore status, further search

helper(target, [], 0)
return self.res


Topics: Lambda less Mobile REST