一、
1、
#include<iostream>
#include<algorithm>
using namespace std;
struct node{ //结构体定义点
int x;
int y;
}d[1000];
int main()
{
int n;
while(cin>>n)
{
int xmin,xmax,ymin,ymax; //四个最大最小坐标点
for(int i=0;i<n;i++)
{
cin>>d[i].x>>d[i].y;
}
xmin=d[0].x; //赋初始值
xmax=d[0].x;
ymin=d[0].y;
ymax=d[0].y;
for(int i=1;i<n;i++)
{
if(xmin>d[i].x){
xmin=d[i].x;
}
if(xmax<d[i].x){
xmax=d[i].x;
}
if(ymin>d[i].y){
ymin=d[i].y;
}
if(ymax<d[i].y){
ymax=d[i].y;
}
}
int l;
l=max(xmax-xmin,ymax-ymin); //求出面积
cout<<l*l;
}
return 0;
}
通过率36% ,由于忽略了int 的范围。
int 范围 [-2^31 , 2^31 -1] 即 [-2147483648,2147483647]
所以很容易溢出。
出错
2、
#include<iostream>
#include<algorithm>
using namespace std;
struct node{ //结构体定义点
long long x,y;
}d[1000];
int main()
{
int n;
while(cin>>n)
{
long long xmin,xmax,ymin,ymax; //四个最大最小坐标点
for(int i=0;i<n;i++)
{
cin>>d[i].x>>d[i].y;
}
xmin=d[0].x; //赋初始值
xmax=d[0].x;
ymin=d[0].y;
ymax=d[0].y;
for(int i=1;i<n;i++)
{
if(xmin>d[i].x){
xmin=d[i].x;
}
if(xmax<d[i].x){
xmax=d[i].x;
}
if(ymin>d[i].y){
ymin=d[i].y;
}
if(ymax<d[i].y){
ymax=d[i].y;
}
}
long long l;
l=max(xmax-xmin,ymax-ymin); //求出面积
cout<<(l*l);
}
return 0;
} // 2 800000000 900000000 -800000000 -900000000
用 long long 数据格式才可以。
各种数据类型范围
二、
#include<iostream>
#include<algorithm>
#include<vector>
#include<set>
using namespace std;
struct Que{
int s;
int e;
};
int N[2001]={0};
int ans[1000000]={0};
int Inqury(int a,int b,int *q)
{
set<int> s;
for(int i=a;i<=b;i++)
{
s.insert(q[i]);
}
return s.size();
}
int main()
{
int n,m,q;
while(cin>>n>>m)
{
for(int i=1;i<=n;i++)
{
cin>>N[i];
}
cin>>q;
for(int i=0;i<q;i++)
{
int s,e,Num;
cin>>s>>e;
Num=Inqury(s,e,N);
ans[i]=Num;
}
for(int i=0;i<q;i++)
{
cout<<ans[i]<<endl;
}
}
}
测试用例:
8 6
1 3 2 2 4 2 5 6
3
1 3
2 5
1 6
三、
四、
1、
1.1
public static int win1(int[] arr) {
if (arr == || arr.length == 0) {
return 0;
}
return Math.max(f(arr, 0, arr.length - 1), s(arr, 0, arr.length - 1));
}
public static int f(int[] arr, int i, int j) {
if (i == j) {
return arr[i];
}
return Math.max(arr[i] + s(arr, i + 1, j), arr[j] + s(arr, i, j - 1));
/*当i!=j时,说明至少还有两张纸牌,那么先手的人就有选择,是先拿第一张,还是拿最后一张。
如果拿了第一张,那么剩下i+1到j的牌里他就是后手,
同理先拿了最后一张,那么他在i到j-1里后手。
都是绝对理性的个体,所以两者选大的拿走即为他的分数。*/
}
public static int s(int[] arr, int i, int j) {
if (i == j) {
return 0;
}
return Math.min(f(arr, i + 1, j), f(arr, i, j - 1));
/*当i!=j时,说明至少还有两张纸牌,那么先手的人就有选择,是先拿第一张,还是拿最后一张。
如果拿了第一张,那么后手的人在剩下i+1到j的牌里他就是先手,
同理如果先手拿了最后一张,那么后手的人在i到j-1里先手。
都是绝对理性的个体,所以先手一定会把更小的留给他。*/
}
1.2 动态规划 解法
#include <iostream>
#include <vector>
#include<string.h>
using namespace std;
int cardGame(vector<int> A, int n) { //纸牌博弈
int dp[n][n]={0};
int dp1[n][n]={0}; //置0;
//memset(dp,0,sizeof(dp));
//memset(dp1,0,sizeof(dp1)); //置0 的另一种方法,库为 string.h
for(int j = 0 ;j < n ; j++)
{
dp[j][j] = A[j];
for(int i = j - 1;i >= 0; i--)
{
dp[i][j] = max((A[i] + dp1[i + 1][j]) , (A[j] + dp1[i][j - 1]));
dp1[i][j] = min(dp[i + 1][j] , dp[i][j - 1]);
}
}
cout<<endl;
for(int i=0;i<n;i++)
{
for(int j=0;j<n;j++)
cout<<dp[i][j]<<" ";
cout<<endl;
}
cout<<endl;
for(int i=0;i<n;i++)
{
for(int j=0;j<n;j++)
cout<<dp1[i][j]<<" ";
cout<<endl;
}
cout<<endl;
return max(dp[0][n - 1],dp1[0][n - 1]);
}
int main()
{
int T = 0;
cin >> T; //测试用例数
vector<int> vec;
for(int i=0;i<T;i++)
{
int tem;
cin>>tem;
vec.push_back(tem);
}
cout<<cardGame(vec,T);
return 0;
} //4 1 2 100 4
//6 4 7 2 9 5 2
// 4 4 7 2 2
3、来回挑最大的
#include <iostream>
#include <vector>
#include<string.h>
using namespace std;
int main()
{
int T = 0;
cin >> T; //测试用例数
vector<int> vec;
for(int i=0;i<T;i++)
{
int tem;
cin>>tem;
vec.push_back(tem);
}
int a=0,b=0;
int flag=0;
while(vec.size()>0)
{
if(flag==0)
{
a+=max(vec[0],vec[vec.size()-1]);
if(vec[0]>=vec[vec.size()-1])
vec.erase(vec.begin());
else
vec.pop_back();
flag=1;
}
else
{
b+=max(vec[0],vec[vec.size()-1]);
if(vec[0]>=vec[vec.size()-1])
vec.erase(vec.begin());
else
vec.pop_back();
flag=0;
}
}
cout<<a<<" "<<b;
return 0;
} //4 1 2 100 4
//6 4 7 2 9 5 2
// 4 4 7 2 2
该题是上题的变形。
五、内存管理
#include <iostream>
#include <vector>
#include <string>
using namespace std;
struct mem //定义结构体
{
int no; //编号,内存,开始,结束
int size;
int start;
int end;
};
vector<mem> vec;
int cnt = 0;
int tail;
int del(int no)
{
for (vector<mem>::iterator it = vec.begin(); it != vec.end(); it++)
{
if ((*it).no == no)
{
vec.erase(it);
return no;
}
}
return -1;
}
int def()
{
for (vector<mem>::iterator it = vec.begin() + 1; it != vec.end() - 1; it++)
{
if ((*it).no == 0)
{
continue;
}
(*it).start = (*(it - 1)).end + 1;
(*it).end = (*it).start + (*it).size - 1;
}
if (vec.size() == 2)
{
tail = (*(vec.end() - 1)).start;
}
else
{
tail = (*(vec.end() - 1)).start - (*(vec.end() - 2)).end - 1;
}
return -1;
}
int newMem(int sz)
{
for (vector<mem>::iterator it = vec.begin() + 1; it != vec.end(); it++)
{
if ((*it).start - (*(it - 1)).end - 1 >= sz)
{
cnt++;
mem tmp = { cnt, sz, (*(it - 1)).end + 1, (*(it - 1)).end + sz };
vec.insert(it, 1, tmp);
tail -= sz;
return cnt;
}
}
vector<mem>::reverse_iterator it = vec.rbegin();
if (tail >= sz)
{
cnt++;
vec.push_back({ cnt, sz, (*it).end + 1, (*it).end + sz });
tail -= sz;
return cnt;
}
return -1;
}
int main()
{
int n = 0;
while (cin >> n >> tail) //n,输入任务 ;tail内存
{
vec.clear();
cnt = 0;
vec.push_back({ 0, 0, -1, -1 });
vec.push_back({ 0, 0, tail, -1 });
string str;
while (n--)
{
cin >> str;
if (str.compare("new") == 0)
{
int sz;
cin >> sz;
int res = newMem(sz);
if (res == -1)
{
//printf("NULL\n");
cout<<"NULL"<<endl;
}
else
{
cout << res << endl;
}
}
else if (str.compare("del") == 0) //删除
{
int tmp;
cin >> tmp;
if (tmp <= 0)
{
//printf("ILLEGAL_OPERATION\n");
cout<<"ILLEGAL_OPERATION"<<endl;
}
else
{
int res = del(tmp);
if (res == -1)
{
//printf("ILLEGAL_OPERATION\n");
cout<<"ILLEGAL_OPERATION"<<endl;
}
}
}
else //def
{
def();
}
for(int i=0;i<vec.size();i++)
{
cout<<vec[i].no<<" "<<vec[i].size<<" "<<vec[i].start<<" "<<vec[i].end<<endl;
}
}
}
return 0;
}
样例
6 10
new 5
new 3
del 1
new 6
def
new 6
2、
#include <iostream>
#include <vector>
#include <string>
using namespace std;
struct mem //定义结构体
{
int no; //编号,内存,开始,结束
int size;
int start;
int end;
};
vector<mem> vec;
int cnt = 0;
int tail;
int del(int no)
{
for (int i=0; i<vec.size(); i++)
{
if (vec[i].no == no)
{
vec.erase(vec.begin()+i);
return no;
}
}
return -1;
}
int def()
{
for (int i =1; i<vec.size() - 1; i++)
{
if (vec[i].no == 0)
{
continue;
}
vec[i].start = vec[i-1].end + 1;
vec[i].end = vec[i].start + vec[i].size - 1;
}
return -1;
}
int newMem(int sz)
{
for (int i= 1; i< vec.size(); i++)
{
if (vec[i].start - vec[i-1].end - 1 >= sz)
{
cnt++;
mem tmp = { cnt, sz, vec[i-1].end + 1, vec[i-1].end + sz };
vec.insert(vec.begin()+i, 1, tmp);
return cnt;
}
}
return -1;
}
int main()
{
int n = 0;
while (cin >> n >> tail) //n,输入任务 ;tail内存
{
vec.clear();
cnt = 0;
vec.push_back({ 0, 0, -1, -1 });
vec.push_back({ 0, 0, tail, -1 });
string str;
while (n--)
{
cin >> str;
if (str.compare("new") == 0)
{
int sz;
cin >> sz;
int res = newMem(sz);
if (res == -1)
{
cout<<"NULL"<<endl;
}
else
{
cout << res << endl;
}
}
else if (str.compare("del") == 0) //删除
{
int tmp;
cin >> tmp;
if (tmp <= 0)
{
cout<<"ILLEGAL_OPERATION"<<endl;
}
else
{
int res = del(tmp);
if (res == -1)
{
cout<<"ILLEGAL_OPERATION"<<endl;
}
}
}
else //def
{
def();
}
for(int i=0;i<vec.size();i++)
{
cout<<vec[i].no<<" "<<vec[i].size<<" "<<vec[i].start<<" "<<vec[i].end<<endl;
}
}
}
return 0;
}
将迭代器换成了下标表示。
1 5 0 4 分别表示第1个任务,占据5个内存,内存地址开始为0,结束为4
2 3 5 7 表示第2个任务,占据3个内存,内存地址开始为5,结束为7
0 0 10 -1 默认存储最大值为10
del 就是查询下标,vector 删除
new 依次查询,相邻任务间的内存差值,大于要存的内容,就保存。例如,上面任务2存在位置5到7,占了3个内存。所以用2号任务开始的地址减去上一个任务结束的地址,可以知道他们之间有了5-(-1)-1=5的内存空间,如果该内存空间大于目标内存,就可以将目标内存存在该处;
def 首先找到任务编号为1的任务,然后将其开始内存地址置为0( vec[i-1].end + 1;),然后结束坐标地址为开始地址加上内存空间;下一个任务,开始地址为上一个任务结束地址+1;
这样就实现了内存管理。