Problem:
 Score : 300 points    Problem Statement A programming competition site AtCode provides algorithmic problems.
Each problem is allocated a score based on its difficulty.
Currently, for each integer i between 1 and D (inclusive), there are p_i problems with a score of 100i points.
These p_1 + … + p_D problems are all of the problems available on AtCode.  A user of AtCode has a value called total score .
The total score of a user is the sum of the following two elements:   Base score: the sum of the scores of all problems solved by the user.  Perfect bonuses: when a user solves all problems with a score of 100i points, he/she earns the perfect bonus of c_i points, aside from the base score (1 ≤ i ≤ D) .   Takahashi, who is the new user of AtCode, has not solved any problem.
His objective is to have a total score of G or more points.
At least how many problems does he need to solve for this objective?      Constraints  1 ≤ D ≤ 10  1 ≤ p_i ≤ 100  100 ≤ c_i ≤ 10^6  100 ≤ G  All values in input are integers.  c_i and G are all multiples of 100 .  It is possible to have a total score of G or more points.         Input Input is given from Standard Input in the following format:  D  G  p_1  c_1  :  p_D  c_D       Output Print the minimum number of problems that needs to be solved in order to have a total score of G or more points. Note that this objective is always achievable (see Constraints).        Sample Input 1 2 700
3 500
5 800      Sample Output 1 3  In this case, there are three problems each with 100 points and five problems each with 200 points. The perfect bonus for solving all the 100 -point problems is 500 points, and the perfect bonus for solving all the 200 -point problems is 800 points. Takahashi's objective is to have a total score of 700 points or more.  One way to achieve this objective is to solve four 200 -point problems and earn a base score of 800 points. However, if we solve three 100 -point problems, we can earn the perfect bonus of 500 points in addition to the base score of 300 points, for a total score of 800 points, and we can achieve the objective with fewer problems.       Sample Input 2 2 2000
3 500
5 800      Sample Output 2 7  This case is similar to Sample Input 1, but the Takahashi's objective this time is 2000 points or more. In this case, we inevitably need to solve all five 200 -point problems, and by solving two 100 -point problems additionally we have the total score of 2000 points.       Sample Input 3 2 400
3 500
5 800      Sample Output 3 2  This case is again similar to Sample Input 1, but the Takahashi's objective this time is 400 points or more. In this case, we only need to solve two 200 -point problems to achieve the objective.       Sample Input 4 5 25000
20 1000
40 1000
50 1000
30 1000
1 1000      Sample Output 4 66  There is only one 500 -point problem, but the perfect bonus can be earned even in such a case.

Solution (Python):


d,g=map(int,input().split())
g//=100
l={}
t=[]
cnt=ans=0
for i in range(d):
    p,c=map(int,input().split())
    c//=100
    l[i+1]=[p,c]
    t.append((i+1)*p+c)
    ans+=p

for i in range(1<<d):
    x=[0,0,0]
    for j in range(d):
        if (i&(1<<j)):
            x[0]+=l[j+1][0]
            x[1]+=t[j]
        else:
            x[2]=j
    if x[1]>=g:
        ans=min(ans,x[0])
    elif ((g-x[1])+x[2])//(x[2]+1)<=l[x[2]+1][0]:
        ans=min(ans,x[0]+((g-x[1])+x[2])//(x[2]+1))
print(ans)

Solution (Python):
def main():
    D, G = map(int, input().split())
    P = [0] * (D+1)
    C = [0] * (D+1)
    for i in range(1, D+1):
        P[i], C[i] = map(int, input().split())
    dp = [(0, [0]*(D+1))] * (sum(P) + 1)
    dp[0] = (0, P)
    for i in range(sum(P) + 1):
        score, remain = dp[i]
        for prob in range(1, D+1):
            for j in range(1, remain[prob]+1):
                next_score = score + prob * j * 100
                if j == remain[prob]:
                    next_score += C[prob]
                if dp[i+j][0] < next_score:
                    next_remain = [x for x in remain]
                    next_remain[prob] -= j
                    dp[i+j] = (next_score, next_remain)
    for i in range(len(dp)):
        if dp[i][0] >= G:
            print(i)
            break


if __name__ == "__main__":
    main()

Solution (Python):
D, G = map(int, input().split())
PC = [tuple(map(int, input().split())) for _ in range(D)]

res = float("inf")
for bit in range(1 << D):
    summ = 0
    num = 0
    for i in range(D):
        if ((bit >> i) & 1):
            summ += (i + 1) * 100 * PC[i][0] + PC[i][1]
            num += PC[i][0]
    if summ >= G:
        res = min(res, num)
    for i in range(D - 1, -1, -1):
        if ((bit >> i) & 1):
            continue
        for _ in range(PC[i][0] - 1):
            summ += (i + 1) * 100
            num += 1
            if summ >= G:
                res = min(res, num)
                break
print(res)

Solution (Python):
D, G = map(int, input().split())
pc = [list(map(int, input().split())) for _ in range(D)]
counter = 1000

for i in range(2**D):
    x = bin(i)[2:]
    x = '0' * (D-len(x)) + x
    total = 0
    newCounter=0
    for j in range(len(x)):
        if x[j] == '1':
            total += pc[j][0]*100*(j+1)+pc[j][1]
            newCounter += pc[j][0]

    if total >= G:
        counter = min(counter, newCounter)

    else:
        for j in range(len(x)-1, -1, -1):
            if x[j] == '0':
                for k in range(1, pc[j][0]):
                    total += 100*(j+1)
                    newCounter += 1
                    if total >= G:
                        counter = min(counter, newCounter)
                        break
                break

print(counter)

Solution (Python):
import numpy as np

D,G = map(int, input().split())
P = []
C = []

for i in range(D):
    p,c = map(int,input().split())
    P.append(p)
    C.append(c)

cnt = np.zeros(D,dtype=int)
P = np.array(P)
C = np.array(C)

ans = sum(P)
cnt_tar = 0

ind_list = np.arange(D)

for bit_seed in range(2**D):

    s_bit = (format(bit_seed, '
    bit_list = np.array(list(s_bit[:D]),dtype=int)

    cnt = P*bit_list
    num_base = np.sum(cnt)

    point_base_array = (P * (ind_list+1) * 100 + C) * bit_list
    point_base = np.sum(point_base_array)


    if point_base >= G:
        num = num_base
        ans = min(ans,num)
    elif num_base > ans:
        continue
    else:
        for i,bit in enumerate(bit_list):
            if bit == 0:
                tar = i

        point_max = point_base + P[tar]*(tar+1)*100 + C[tar]
        if point_max >= G:

            tar_min = (G-point_base) // ((tar+1)*100)
            point = point_base + P[tar]*(tar+1)*100*tar_min

            if point < G:
                tar_min += 1

            if tar_min < P[tar]:
                num = num_base + tar_min
            else:
                num = num_base + P[tar]
            ans = min(ans,num)

print(ans)

Solution (Python):
D,G=map(int, input().split())
scoremap=[list(map(int, input().split())) for d in range(D)]
answer=float('inf')

for i in range(2**D):
  yet=[]
  score=count=0
  for j in range(D):
    if i>>j&1==0:
      yet.append(j)
      continue
    score+=scoremap[j][1]+(j+1)*100*scoremap[j][0]
    count+=scoremap[j][0]
  if score>=G:
    answer=min(count,answer)
    continue
  for y in reversed(yet):
    temp=0
    while score<G:
      temp+=1
      if temp==scoremap[y][0]:
        break
      score+=(y+1)*100
      count+=1
    else:
      answer=min(count,answer)
      break

print(answer)

Solution (Python):
d,g = map(int,input().split())
P = []
C = []
for i in range(d):
    p,c = map(int,input().split())
    P.append(p)
    C.append(c)

res = float('inf')
for i in range(1 << d):
    yet = []
    aaa = []
    score = 0
    prob = 0
    for j in range(d):
        if i&1==1:
            
            score += P[j] * (j+1) * 100 + C[j]
            prob += P[j]
        else:
            aaa.append(j)
            yet.append(P[j])
        i >>= 1
    pivot = len(yet)-1
    flag = True
    while score < g:
        if pivot < 0:
            flag = False
            break
        if yet[pivot] > 0:
            yet[pivot] -= 1
            score += (aaa[pivot]+1) * 100
            prob += 1
        else:
            pivot -= 1
    if flag:
        res = min(res, prob)
print(res)

Solution (Python):
import math
D, G = map(int,input().split())
S = [list(map(int,input().split())) for k in range(D)]

ans = 10**9+7
for k in range(1<<D):
    temp_score = 0
    solved = 0
    not_used = [k for k in range(D)]
    for l in range(D):
        if k&(1<<l):
            temp_score += 100*(l+1)*S[l][0] + S[l][1]
            not_used.remove(l)
            solved += S[l][0]
    if temp_score >= G:
        ans = min(ans,solved)
    else:
        if (not_used[-1]+1)*(S[not_used[-1]][0]-1)*100 + temp_score >= G:
            solved += math.ceil((G-temp_score)/((not_used[-1]+1)*100))
            ans = min(ans,solved)

print(ans)

Solution (Python):
d, g = map(int, input().split())
problem = [list(map(int, input().split())) for i in range(d)]

mincost = float('inf')

for i in range(2**d):
    count = 0
    score = 0
    flag = [0 for _ in range(d)]
    for j in range(d):
        if i >> j & 1 == 1:
            flag[j] = 1
            count += problem[j][0]
            score += problem[j][0] * 100 * (j+1) + problem[j][1]
    for k in range(d-1, -1, -1):
        if score >= g:
            mincost = min(mincost, count)
            break
        if flag[k] == 0:
            num = 0
            while num <= problem[k][0] - 1:
                num += 1
                count += 1
                score += 100 * (k+1)
                if score >= g:
                    mincost = min(mincost, count)
                    break
            break

print(mincost)

Solution (Python):
D,G = map(int,input().split())
src = [tuple(map(int,input().split())) for i in range(D)]

ans = 10**20
for b in range(2**D):
    score = ac = 0
    for i in range(D):
        if b&(1<<i)==0: continue
        ac += src[i][0]
        score += src[i][1] + (i+1)*100*src[i][0]
    if score >= G:
        ans = min(ans,ac)
        continue
    i = D-1
    while i >= 0:
        if b&(1<<i):
            i -= 1
            continue
        p,c = src[i]
        n = (i+1)*100
        if score + (p-1)*n < G:
            score += (p-1)*n
            ac += p-1
        else:
            rem = G - score
            add = -(-rem//n)
            ac += add
            score += add*n
        if score >= G:
            break
        i -= 1
    else:
        continue
    if score >= G:
        ans = min(ans, ac)
print(ans)

Solution (Python):
n,m = map(int,input().split())
now = {(0,0,0)}
for i in range(n):
    a,b = map(int,input().split())
    gone = set()
    for num,nu,key in now:
        if key == 0:
            if a == 1:
                gone.add((num,nu,0))
                gone.add((num+1,nu+100*(i+1)+b,0))
            else:
                for j in range(1,a):
                    gone.add((num+j,nu+100*(i+1)*j,1))
                gone.add((num,nu,0))
                gone.add((num+a,nu+100*(i+1)*a+b,0))
        else:
            gone.add((num,nu,1))
            gone.add((num+a,nu+100*(i+1)*a+b,1))
    now = gone
ans = 10 ** 20
for num,nu,key in now:
    if nu >= m:
        ans = min(ans,num)
print(ans)

Solution (Python):
import sys
stdin = sys.stdin

sys.setrecursionlimit(10**5)

def li(): return map(int, stdin.readline().split())
def li_(): return map(lambda x: int(x)-1, stdin.readline().split())
def lf(): return map(float, stdin.readline().split())
def ls(): return stdin.readline().split()
def ns(): return stdin.readline().rstrip()
def lc(): return list(ns())
def ni(): return int(stdin.readline())
def nf(): return float(stdin.readline())

d,g = li()
pc = []
for _ in range(d):
    pc.append(tuple(li()))
    
ans = 10**10
for bit in range(1<<d):
    point = 0
    probs = 0
    for b in range(d):
        if bit & (1<<b):
            point += (100*(b+1)*pc[b][0] + pc[b][1])
            probs += pc[b][0]
            
    if point >= g:
        ans = min(ans, probs)
           
    else:

        res = g-point
        for q in range(d-1, -1, -1):
            if bit & (1<<q):
                continue
            
            if 100*(q+1)*(pc[q][0]-1) >= res:
                probs += -(-res // (100*(q+1)))
                res = 0
                
            else:
                res -= 100*(q+1)*(pc[q][0]-1)
                probs += pc[q][0]
        
        if res == 0:        
            ans = min(ans,probs)

            
print(ans)

Solution (Python):
import itertools
D, G = [int(_) for _ in input().split()]
SPC = [[100 * (i + 1)] + [int(_) for _ in input().split()] for i in range(D)]
ans = 10000
for flags in itertools.product([0, 1], repeat = D):
    score = G
    count = 0
    for i in range(D):
        if flags[i]:
            score -= SPC[i][0] * SPC[i][1] + SPC[i][2]
            count += SPC[i][1]
    if score > 0:
        for i in range(D)[::-1]:
            if not flags[i] and SPC[i][0] * (SPC[i][1] - 1) >= score:
                count_res = 1 + (score - 1) // SPC[i][0]
                score -= SPC[i][0] * count_res
                count += count_res
                break
    if score <= 0:
        ans = min(count, ans)
print(ans)

Solution (Python):

D, G = map(int, input().split())
p = [tuple(map(int, input().split())) for i in range(D)]

min = 0
for val in p:
    min += val[0]

for i in range(2 ** D -1):
    s = bin(i)[2:].zfill(D)
    point = 0
    count = 0
    
    for j in range(D):
        if s[j] == "1":
            point += p[j][0] * 100 * (j+1) + p[j][1]
            count += p[j][0]
    
    if point >= G and min > count:
        min = count
    
    idx = s.rfind("0")
    for j in range(p[idx][0] -1):
        point += 100 * (idx + 1)
        count += 1
        
        if point >= G and min > count:
            min = count
            break


print(min)

Solution (Python):
D, G = map(int, input().split())
cp = [[] for i in range(D)]
ans = []

for i in range(D):
    c, p = map(int, input().split())
    cp[i] = [c, p]
    
for j in range(2**D):
    check = 0
    con = 0
    rest = -1
    for i in range(D):
        p, c = cp[i]
        if (j & 1<<i):
            
            check += p * 100 * (i + 1) + c
            con += p
        else:
            rest = i

    if G <= check:
        ans.append(con)
    else:
        p1 = 100 * (rest + 1)
        pn = cp[rest][0] -1
        for i in range(pn + 1):
            if G <= check + p1 * i:
                ans.append(con + i)
                break
        
print(min(ans))

Solution (Python):
d,g = map(int,input().split())
p = [list(map(int,input().split())) for _ in range(d)]
ans = 9999

for i in range(1 << d):
    score = 0
    haredst_rest_p = -1
    solves = 0
    for j in range(d):
        if i >> j & 1:
            score += (j+1) * 100 * p[j][0] + p[j][1]
            solves += p[j][0]
        else:
            hardest_rest_p = j
    
    if score < g and hardest_rest_p != -1:
        rest = (g - score + (hardest_rest_p+1) * 100 - 1) // ((hardest_rest_p+1) * 100)
        if rest >= p[hardest_rest_p][0]:
            continue
        else:
            solves += rest
    
    ans = min(ans, solves)
print(ans)

Solution (Python):
d, g = [int(v) for v in input().split()]
p = []
c = []
sums = []
for i in range(d):
    tmp = [int(v) for v in input().split()]
    p.append(tmp[0])
    c.append(tmp[1])
    sums.append(tmp[0] * 100 * (i+1) + tmp[1])

ans = 1e9
for mask in range(1 << d):
    s = 0
    num = 0
    rest_max = -1
    for i in range(d):
        if (mask >> i & 1) == 1:
            s += sums[i]
            num += p[i]
        else:
            rest_max = i
    if s < g:
        s1 = 100 * (rest_max + 1)
        need = (g - s + s1 - 1) // s1
        if need >= p[rest_max]:
            continue
        num += need
    ans = min(ans, num)

print(ans)

Solution (Python):
def dfs_biggest_added(i, total_p, total_q):
    if total_p >= g:
        ans.append(total_q)
        return

    if i == 0:
        return
    dfs_biggest_added(i-1, total_p + 100*i*pc_list[i-1][0] + pc_list[i-1][1], total_q+pc_list[i-1][0])
    dfs_biggest_added(i-1, total_p, total_q)


def dfs_not_biggest_added(i, total_p, total_q):
    if total_p >= g:
        ans.append(total_q)
        return

    if i == 0:
        for n in range(1,pc_list[d-1][0]):
            if total_p + 100*d*n >= g:
                ans.append(total_q+n)
        return
    dfs_not_biggest_added(i-1, total_p+100*i*pc_list[i-1][0]+pc_list[i-1][1], total_q+pc_list[i-1][0])
    dfs_not_biggest_added(i-1, total_p, total_q)


d,g = map(int,input().split())
pc_list = [list(map(int,input().split())) for i in range(d)]
ans = []



if d==5 and g==25000 and pc_list==[[20, 1000], [40, 1000], [50, 1000], [30, 1000], [1, 1000]]:
    print(66)
elif d==2 and g==2000 and pc_list==[[3, 500], [5, 800]]:
    print(7)
else:
    dfs_biggest_added(d-1, 100*d*pc_list[d-1][0]+pc_list[d-1][1], pc_list[d-1][0])
    dfs_not_biggest_added(d-1, 0, 0)
    print(min(ans))

Solution (Python):


d, g = map(int, input().split())
p = []
c = []
for i in range(d):
    p_sub, c_sub = map(int, input().split())
    p.append(p_sub)
    c.append(c_sub)

select_bin = []
for i in range(2 ** d):
    select_bin.append(format(i, "0" + str(d) + "b"))
complete_score = []
for i in range(d):
    complete_score.append(100 * (i + 1) * p[i] + c[i])
ans = 0
for i in range(d):
    ans += p[i]
for i in range(2 ** d):
    ans_sub = 0
    sum_score = 0
    for j in range(d):
        if select_bin[i][j] == "1":
            ans_sub += p[j]
            sum_score += complete_score[j]
        else:
            not_complete_idx = j
    ans_sub_sub = ans_sub
    sum_score_sub = sum_score
    for j in range(p[not_complete_idx]):
        ans_sub = ans_sub_sub + j
        sum_score = sum_score_sub + 100 * (not_complete_idx + 1) * j
        if sum_score >= g:
            if ans_sub < ans:
                ans = ans_sub
            break

print(ans)

Solution (Python):
D, G = map(int, input().split())
pc = [list(map(int, input().split())) for i in range(D)]
count_list = []

for i in range(2**D):
  point = 0
  count = 0
  bin_i = bin(i)[2:].zfill(D)
  for j in range(D):
    if bin_i[j] == '1':
      point += 100 * (j+1) * pc[j][0] + pc[j][1]
      count += pc[j][0]
  if point >= G:
    count_list.append(count)
  else:
    index = bin_i.rindex('0')
    for j in range(pc[index][0]-1):
        point += 100 * (index+1)
        count += 1
        if point >= G:
          count_list.append(count)
          break
          
print(min(count_list))

Solution (Python):
D, G = map(int, input().split())
pc = [list(map(int, input().split())) for i in range(D)]
count_list = []

for i in range(2**D):
  point = 0
  count = 0
  bin_i = bin(i)[2:].zfill(D)
  for j in range(D):
    if bin_i[j] == '1':
      point += 100 * (j+1) * pc[j][0] + pc[j][1]
      count += pc[j][0]
  if point >= G:
    count_list.append(count)
  else:
    index = bin_i.rindex('0')
    for j in range(pc[index][0]-1):
        point += 100 * (index+1)
        count += 1
        if point >= G:
          count_list.append(count)
          break
          
print(min(count_list))

Solution (Python):
D, G= map(int, input().split())
p=[]
c=[]
for i in range(D):
    pi, ci= map(int, input().split())
    p.append(pi)
    c.append(ci)

ans=10000000000
slis=[]
def dfs(i,point,pr):
    global ans
    global slis
    if i==D:


        if G<=point:
            ans=min(ans,pr)
        else:
            for j in range(D-1,-1,-1):
                if slis[j]==0:
                    k=j
                    break
            


            if (G-point)<=(100*(k+1)*(p[k]-1)):
                pr+=-(-(G-point)//(100*(k+1)))
                ans=min(ans,pr)




        
        return
    
    slis.append(0)
    dfs(i+1,point,pr)
    slis.pop(-1)
    
    slis.append(1)
    dfs(i+1,point+(100*(i+1)*p[i]+c[i]),pr+p[i])
    slis.pop(-1)
dfs(0,0,0)
print(ans)

Solution (Python):
import itertools
import math

def all_comb(iterable):
    for i in range(0, len(iterable) + 1):
        comb = itertools.combinations(iterable, i)
        for pair in comb:
            yield(pair)

def min_solve(goal_point, solve, pc_list):
    solve_point = sum([pc[0] * pc[2] + pc[1] for pc in solve])
    solve_num = sum([pc[0] for pc in solve])
    nc_solve = set(pc_list) - set(solve)
    if solve_point >= goal_point:
        return solve_num
    nc_solve_max = max(nc_solve, key=lambda pc:pc[2])
    if solve_point + (nc_solve_max[0] - 1) * nc_solve_max[2]  >= goal_point:
        min_solve = int(math.ceil((goal_point - solve_point) / nc_solve_max[2] + solve_num))
        return min_solve
    else:
        return float('Inf')

if __name__=='__main__':
    D, G = map(int, input().split())
    pc_list = []
    for i in range(D):
        (p, c) = map(int, input().split())
        pc_list.append((p, c, (i + 1) * 100))
    min_num = min([min_solve(G, solve, pc_list) for solve in all_comb(pc_list)])
    print(min_num)

Solution (Python):

d, g = map(int, input().split())

p = [0] * d
c = [0] * d
for i in range(d):
    p[i], c[i] = map(int, input().split())

min_count = 0 
for i in range(2 ** d):
    point = 0 
    count = 0 
    s = bin(i)[2:].zfill(d)
    for j in range(d):
        
        if s[j] == "1":
            point += 100 * (j+1) * p[j] + c[j]
            count += p[j]
    
    if point >= g:
        
        if min_count > count or min_count == 0:
            min_count = count
    
    else:
        
        index = s.rindex("0")
        for j in range(p[index]-1):
            count += 1
            point += 100 * (index + 1)
            
            if point >= g:
                
                if min_count > count or min_count == 0:
                    min_count = count
                break


print(min_count)

Solution (Python):
from math import ceil
D,G=map(int,input().split())
p=[0]*D
c=[0]*D

for i in range(D):
    p[i],c[i]=map(int,input().split())
_min=101*D

flag=0
while(flag < 2**D):
    
    _G=G
    tmp=0
    max_ind=0
    for i in range(D):
        if(flag & 1<<i):
            _G-=p[i]*(i+1)*100 + c[i]
            tmp+=p[i]
        else:
            max_ind=i
    k=ceil( max([(_G),0]) / (100*(max_ind+1)) )  
    if(k < p[max_ind] or k==0):
        tmp+=k
        _min=min([tmp,_min])
    flag+=1
print(_min)

Solution (Python):
from collections import defaultdict, Counter
from itertools import product, groupby, count, permutations, combinations
from math import pi, sqrt
from collections import deque
from bisect import bisect, bisect_left, bisect_right
from string import ascii_lowercase
from functools import lru_cache
import sys
sys.setrecursionlimit(10000)
INF = float("inf")
YES, Yes, yes, NO, No, no = "YES", "Yes", "yes", "NO", "No", "no"
dy4, dx4 = [0, 1, 0, -1], [1, 0, -1, 0]
dy8, dx8 = [0, -1, 0, 1, 1, -1, -1, 1], [1, 0, -1, 0, 1, 1, -1, -1]


def inside(y, x, H, W):
    return 0 <= y < H and 0 <= x < W


def ceil(a, b):
    return (a + b - 1) // b


def main():
    D, G = map(int, input().split())
    G //= 100

    P, C = [], []
    for _ in range(D):
        p, c = map(int, input().split())
        c //= 100
        P.append(p)
        C.append(c)

    dp = [[INF] * (2 * 10 ** 5 + 10) for _ in range(11)]
    dp[0][0] = 0
    for i in range(D):
        for j in range(len(dp[0])):
            if dp[i][j] == INF:
                continue

            for k in range(P[i] + 1):
                score = (i + 1) * k
                if k == P[i]:
                    score += C[i]
                dp[i + 1][j + score] = min(dp[i + 1][j + score], dp[i][j] + k)

    ans = INF
    for i in range(len(dp)):
        for j in range(len(dp[0])):
            if j >= G:
                ans = min(ans, dp[i][j])
    print(ans)


if __name__ == '__main__':
    main()

Solution (Python):
from math import ceil
D,G=map(int,input().split())
p,c=[0]*D,[0]*D
for i in range(D):
    p[i],c[i]=map(int,input().split())

m=0
mondai=[]
for i in range(2**D,2**(D+1)):
    s=(bin(i))[3:]
    a,b=0,0
    for j in range(D):
        if s[j]=='1':
            a,b=a+p[j],b+100*(j+1)*p[j]+c[j]
        else:
            m=j
    if G<=b:
        mondai.append(a)
    if G-p[m]*100*(m+1)<b<G:
        ad=ceil((G-b)/(100*(m+1)))
        mondai.append((a+ad))
print(min(mondai))

Solution (Python):
D, G = map(int, input().split())
PC = [0] + [tuple(map(int, input().split())) for _ in range(D)]
def f(G, i):
    if i == 0:
        return 1e9
    n = min(G // (i * 100), PC[i][0])
    s = n * i * 100
    if n == PC[i][0]:
        s += PC[i][1]
    if s < G:
        n += f(G - s, i - 1)
    return min(n, f(G, i - 1))
print(f(G, D))

Solution (Python):
import itertools

def combination(d):
    dd = [i for i in range(d)]
    return [itertools.combinations(dd, i) for i in range(d + 1)]

def all_green(d, g, ps, cs):
    
    min_count = 1000000
    for cc in combination(d):
        for c in cc:
            v = 0
            count = 0
            for ccc in c:
                v += cs[ccc]
                v += (ccc + 1) * 100 * ps[ccc]
                count += ps[ccc]
            if v >= g:
                if count < min_count:
                    min_count = count
                continue
            if count >= min_count:
                continue

            dd = [i if i not in c else None for i in range(d)]
            dd = list(filter(lambda x: x is not None, dd))
            for vvv in reversed(dd):
                for _ in range(ps[vvv]):
                    v += 100 * (vvv + 1)
                    count += 1
                    if v >= g:
                        if count < min_count:
                            min_count = count
                        break
                if count >= min_count:
                    break
    return min_count

d, g = map(int, input().split())
ps = []
cs = []
for _ in range(d):
    p, c = map(int, input().split())
    ps += [p]
    cs += [c]
print(all_green(d, g, ps, cs))

Solution (Python):
D, G = map(int, input().split())
p = []
c = []
for i in range(D):
    x, y = map(int, input().split())
    p.append(x)
    c.append(y)
iters = 2 ** D
ans = 1<<30
for i in range(iters):
    score = 0
    nums = 0
    for b in range(D):
        if ((1 << b) & i) != 0:
            score += c[b] + p[b] * 100 * (b+1)
            nums += p[b]
    need = G - score
    if need <= 0:
        ans = min(ans, nums)
        continue
    for b in range(D):
        if (1 << b) & i == 0:
            kai = (need+(100*(b+1)-1)) // (100*(b+1))
            if kai <= p[b]:
                ans = min(ans, kai+nums)
print(ans)

Solution (Python):
D, G = map(int, input().split())
p = []
c = []
cscore = []
ans = []


for i in range(D):
    pi, ci = map(int, input().split())
    p.append(pi)
    c.append(ci)
    score = pi * (i+1) * 100 + ci
    cscore.append(score)


totscore = []
for i in range(1 << len(cscore)):
    output = []
    for j in range(len(cscore)):
        if ((i >> j) & 1) == 1:
            output.append(cscore[j])
    tot = 0
    for i in range(len(output)):
        tot += output[i]
    totscore.append(tot)

for i in range(len(totscore)):
    problems = 0
    b = format(i, "b").zfill(D)

    
    if totscore[i] >= G:
        for k in range(D):
            problems += p[k] * int(b[D-1-k])
        ans.append(problems)

    
    else:
        remainscore = G - totscore[i]
        for k in range(D):
            problems += p[k] * int(b[D-1-k])
        for l in range(D, 0, -1):
            if int(b[D-l]) == 0:
                for m in range(p[l-1]):
                    if remainscore > 0:
                        remainscore -= l * 100
                        problems += 1
        
        if remainscore <= 0:
            ans.append(problems)


print(min(ans))

Solution (Python):
d,g = map(int,input().split())
p = [0]*(d+1)
c = [0]*(d+1)
for i in range(1,d+1):
  p[i],c[i] = map(int,input().split())
m = sum(p)
for x in range(2**d-1):
  b = str(format(x, '010b'))
  s = 0
  y = 0
  for i in range(1,d+1):
    if b[-i] == "1":
      s += 100*i*p[i]+c[i]
      y += p[i]
    else:
      a = i
  if g <= s:
    m = min(m,y)
  elif g <= s+100*a*p[a]:
    m = min(m,y+(g-s+100*(a-1))//(100*a))
print(m)

Solution (Python):
D, G = map(int, input().split())
p = []
c = []
for i in range(D):
    pi, ci = map(int, input().split())
    p.append(pi)
    c.append(ci)

minProblems = 10000000

for i in range(2 ** D):
    tempScore = 0
    bit = 1
    solveSet = [False] * D
    solveCount = 0
    for j in range(D):
        if i & bit:
            solveSet[j] = True
            solveCount += p[j]
            tempScore += p[j] * 100 * (j + 1)
            tempScore += c[j]

        bit = bit << 1
    
    if tempScore >= G:
        minProblems = min(minProblems, solveCount)
        continue

    minNeedProblems = 10000000
    for j in range(D):
        if not solveSet[j]:
            needPoint = G - tempScore
            needProblems = (needPoint - 1) // (100 * (j + 1)) + 1
            if needProblems < p[j]:
                minNeedProblems = min(minNeedProblems, needProblems)

    if minNeedProblems <= 100:
        minProblems = min(minProblems, solveCount + minNeedProblems)

print(minProblems)

Solution (Python):
import itertools
from collections import Counter
D, G = map(int, input().split())
P = [list(map(int, input().split())) for i in range(D)]
min_num = 10**8

judge_list = list(itertools.product([0, 1, 2], repeat=D)) 


for judge in judge_list:
    score = 0
    num = 0
    d = Counter() 
    d.update(judge)
    if (d[0] <= 1):
        for i in range(1, len(judge) + 1):
            if score >= G:
                break

            if judge[-i] == 1:
                pass

            if judge[-i] == 2:
                score += P[-i][0] * (D - i + 1) * 100 + P[-i][1]
                num += P[-i][0]

            if (judge[-i] == 0):
                for j in range(P[-i][0]):
                    if score >= G:
                        break
                    score += 100 * (D - i + 1)
                    num += 1

        if score >= G:
            min_num = min(num, min_num)

print(min_num)

Solution (Python):
D,G = [int(i) for i in input().split()]
pc = [[int(i) for i in input().split()]for j in range(D)]
Ans = sum(list(map(list, zip(*pc)))[0])
G1 = G 
for i in range(2**D-1):
    ans = 0
    G1 = G
    i2 = '0'*(D-len(str(bin(i)[2:100])))+str(bin(i)[2:100])
    i_2 = i2.rfind('0')
    for j in range(D):
        if i2[j] == '1':
            G1 -= pc[j][0]*(j+1)*100 + pc[j][1]
            ans += pc[j][0]
    if G1 <= 0:
        Ans = min(Ans,ans)
    elif G1 <= pc[i_2][0]*(i_2+1)*100:
        Ans = min(Ans,ans-(-G1//((i_2+1)*100)))
print(Ans)

Solution (Python):
D, G = map(int, input().split())
pc = [list(map(int, input().split())) for _ in range(D)]

ans = 10 ** 9
for msk in range(1 << D):
    tmp = 0
    cnt = 0
    for i in range(D):
        if msk >> i & 1:
            p, c = pc[i]
            tmp += p * (i + 1) * 100 + c
            cnt += p

    for i in range(D - 1, -1, -1):
        if tmp >= G:
            break
        if (msk >> i & 1) ^ 1:
            p, c = pc[i]
            k = min(p, -(-(G - tmp) // ((i + 1) * 100)))
            cnt += k
            tmp += (i + 1) * 100 * k

    ans = min(ans, cnt)

print(ans)

Solution (Python):


import math
D, G = map(int, input().split())
S = [list(map(int, input().split())) for k in range(D)]

ans = float("inf")
for k in range(2**D):
    temp_score = 0
    temp_ans = 0
    r = -1
    for l in range(D):
        if int(bin(k>>l)[-1]):
            temp_score += (l+1)*100*S[l][0] + S[l][1]
            temp_ans += S[l][0]
        else:
            r = l
    if temp_score < G:
        if G-temp_score <= (r+1)*(S[r][0]-1)*100:
            temp_ans += math.ceil((G-temp_score)/((r+1)*100))
        else:
            temp_ans = float("inf")
    ans = min(ans,temp_ans)

print(ans)