#include <iostream>
#include <stdio.h>
#include <cstring>
using namespace std;
int main()
{
freopen("in.txt","r",stdin);
int cash;
bool a[100010];
while (cin>>cash)
{
memset(a,0,sizeof(a));
int n;
cin>>n;
a[0]=1;
int max=0;
for (int i=1;i<=n;i++)
{
int num,v;
cin>>num>>v;
for (int j=max;j>=0;j--) //逆序,保证使用的值是上一层的值,否则会被修改,
//若用二维数组则没问题
{
if (a[j])
{
for (int k=1;k<=num;k++)
if (j+k*v<=cash)
{
a[j+k*v]=1;
if (j+k*v>max) max=j+k*v;
}
}
}
}
cout<<max<<endl;
}
return 0;
}
/*题意:给出一个价值cash,然后给出n,代表n种面值,接着n对代表面值个数与面值,
要求最接近cash,但不超过cash的价值
思路:多重背包,dp数组记录现在的总和是否用过了,然后一直记录最大*/
#include <stdio.h>
#include <cstring>
using namespace std;
int main()
{
freopen("in.txt","r",stdin);
int cash;
bool a[100010];
while (cin>>cash)
{
memset(a,0,sizeof(a));
int n;
cin>>n;
a[0]=1;
int max=0;
for (int i=1;i<=n;i++)
{
int num,v;
cin>>num>>v;
for (int j=max;j>=0;j--) //逆序,保证使用的值是上一层的值,否则会被修改,
//若用二维数组则没问题
{
if (a[j])
{
for (int k=1;k<=num;k++)
if (j+k*v<=cash)
{
a[j+k*v]=1;
if (j+k*v>max) max=j+k*v;
}
}
}
}
cout<<max<<endl;
}
return 0;
}
/*题意:给出一个价值cash,然后给出n,代表n种面值,接着n对代表面值个数与面值,
要求最接近cash,但不超过cash的价值
思路:多重背包,dp数组记录现在的总和是否用过了,然后一直记录最大*/