A. Extract Numbers
【题意】给定一个字符串,把用逗号或分号隔开的子串称为一个word,第一行输出所有由整数组成的word(01,1.0不算整数),第二行输出剩余所有word。不改变word的前后顺序,并用逗号隔开。
【分析】判断word是否为整数时需要注意。
【代码】
#include<cstdio>
#include<iostream>
#include<cstring>
#include<iostream>
#include<vector>
using namespace std;
string s;
string a;
string b;
vector<string> v;
int numbers(int m)
{
int len=v[m].length();
if(len==0) return 0;
for(int i=0;i<len;i++)
{
if(!isdigit(v[m][i])) return 0;
if(len>1&&v[m][0]=='0') return 0;
}
return 1;
}
int main (void)
{
cin>>s;
a='\"';
b='\"';
s+=';';
int begin=0;
for(int i=0;i<=s.length();i++)
{
if(s[i]==';'||s[i]==',')
{
v.push_back(s.substr(begin,i-begin));
begin=i+1;
}
}
for(int i=0;i<v.size();i++)
{
if(numbers(i)) a+=v[i], a+=',';
else b+=v[i], b+=',';
}
a[a.length()-1]='\"';
b[b.length()-1]='\"';
if(a.length()==1 ) cout<<'-'<<endl;
else cout<<a<<endl;
if(b.length()==1) cout<<'-'<<endl;
else cout<<b<<endl;
}
B. Queries about less or equal elements
【分析】(正好用上刚会的upper_bound)将数组排好序,获取第一个大于该值的元素的下标,即为小于等于该值的元素个数。
【代码】
#include<cstdio>
#include<iostream>
#include<cstring>
#include<iostream>
#include<vector>
#include<algorithm>
using namespace std;
const int maxn=200005;
typedef long long ll;
int a[maxn];
int b[maxn];
int c[maxn];
int main (void)
{
int n,m;
cin>>n>>m;
for(int i=0;i<n;i++) cin>>a[i];
sort(a,a+n);
for(int i=0;i<m;i++)
{
cin>>b[i];
c[i]=upper_bound(a,a+n,b[i])-a;
}
for(int i=0;i<m;i++)
cout<<c[i]<<" ";
}
C. Make Palindrome
【题意】更改字符串中的字母,使得重新组合后的字符串是回文串,求最少的变更次数
【分析】贪心,为使最终改变次数最少且字典序最小:首先用数组记录字符串中字母出现次数,并定义两个指针,分别指向a和z,依次逼近。
- 如果一个字母出现次数为偶数,则不改变。
- 如果两个字母出现次数为奇数,则将字典序较大的字母更改成字典序较小的字母。
最后按字典序输出字符串。
【代码】
#include<cstdio>
#include<cstring>
#include<iostream>
#include<vector>
#include<algorithm>
#include<cmath>
using namespace std;
string s;
const int maxn=200005;
int cnt[maxn];
int main (void)
{
cin>>s;
for(int i=0;i<s.length();i++) cnt[s[i]]++;
int begin='a';
int end='z';
int len=s.length();
while(begin<end)
{
while(begin<end&&cnt[begin]%2==0) begin++;
cnt[begin]++;
while(begin<end&&cnt[end]%2==0) end--;
cnt[end]--;
}
int j=0;
for(int i='a';i<='z';i++)
{
while(cnt[i]>=2)
{
s[j]=s[len-j-1]=i;
cnt[i]-=2;
j++;
}
if(cnt[i]==1) s[len/2]=i;
}
cout<<s<<endl;
}
D. Area of Two Circles' Intersection
【题意】给定两个圆的圆心坐标和半径,求两个圆相交的面积
【分析】新get的两个圆相交面积模板
【代码】
#include<cstdio>
#include<cstring>
#include<iostream>
#include<vector>
#include<algorithm>
#include<cmath>
#include<iomanip>
using namespace std;
const long double PI=acos(-1.0);
struct Round
{
long double x,y;
long double r;
long double K(long double x)
{
return x*x;
}
long double Dis(Round a,Round b)
{
return sqrt(K(a.x-b.x)+K(a.y-b.y));
}
long double Intersection_area(Round a,Round b)
{
long double dis=Dis(a,b);
if(a.r==0||b.r==0||dis>=a.r+b.r)return 0;
else if(dis<=fabs(a.r-b.r))return PI*K(min(a.r,b.r));
else
{
long double angA=2*acos( (K(a.r)+K(dis)-K(b.r))/(2*a.r*dis) );
long double angB=2*acos( (K(b.r)+K(dis)-K(a.r))/(2*b.r*dis) );
long double areaA=K(a.r)*(angA-sin(angA))/2;
long double areaB=K(b.r)*(angB-sin(angB))/2;
return areaA+areaB;
}
}
}a,b;
int main()
{
cin>>a.x>>a.y>>a.r>>b.x>>b.y>>b.r;
cout<<setprecision(25)<<a.Intersection_area(a,b)<<endl;
return 0;
}
C题想了好久都不会,后来看了题解才懂。笨死啦~~~