1001
8进制数,直接贴代码。
#include <stdio.h>
int c[1000];
int fun(int t){
int ret=0,mul=1;
while (t!=0){
ret+=mul*c[(t%10)];
mul*=8;
t/=10;
}
return ret;
}
int main(){
c[0]=0;c[1]=1;c[2]=2;
c[4]=3;c[5]=4;c[6]=5;c[7]=6;
c[9]=7;
int n,ret;
while (scanf("%d",&n),n!=0){
printf("%d: %d\n",n,fun(n));
}
return 0;
}
1002
找规律,注意观察平方数。这题不是我做的,木有代码
1003
可以当成很裸的网络流来做,Sap+Gap优化,木有模板怎么破~_~
#include <stdio.h>
#include <string.h>
#include <vector>
#include <queue>
using namespace std;
const int N=2e5+10;
#define VM 100010
#define EM 400010
const int inf = 0x3f3f3f3f;
struct SAP{
struct E
{
int to, frm, nxt, cap;
}edge[EM];
int head[VM],e,n,m;
int dep[VM], gap[VM];
void init(int _n=VM-10,int _m=EM-10)
{
memset(head,-1,sizeof(head));
e=0;
n=_n,m=_m;
}
void addedge(int cu, int cv, int cw)
{
edge[e].frm = cu;
edge[e].to = cv;
edge[e].cap = cw;
edge[e].nxt = head[cu];
head[cu] = e++;
edge[e].frm = cv;
edge[e].to = cu;
edge[e].cap = 0;
edge[e].nxt = head[cv];
head[cv] = e++;
}
int que[VM];
void BFS(int des)
{
memset(dep, -1, sizeof(dep));
memset(gap, 0, sizeof(gap));
gap[0] = 1;
int front = 0, rear = 0;
dep[des] = 0;
que[rear++] = des;
int u, v;
while (front != rear)
{
u = que[front++];
front = front%VM;
for (int i=head[u]; i!=-1; i=edge[i].nxt)
{
v = edge[i].to;
if (edge[i].cap != 0 || dep[v] != -1)
continue;
que[rear++] = v;
rear = rear % VM;
++gap[dep[v] = dep[u] + 1];
}
}
}
int cur[VM],stack[VM];
int Sap(int src,int des) //sap模板
{
int res = 0;
BFS(des);
int top = 0;
memcpy(cur, head, sizeof(head));
int u = src, i;
while (dep[src] < n)
{
if (u == des)
{
int temp = inf, inser = n;
for (i=0; i!=top; ++i)
if (temp > edge[stack[i]].cap)
{
temp = edge[stack[i]].cap;
inser = i;
}
for (i=0; i!=top; ++i)
{
edge[stack[i]].cap -= temp;
edge[stack[i]^1].cap += temp;
}
res += temp;
top = inser;
u = edge[stack[top]].frm;
}
if (u != des && gap[dep[u] -1] == 0)
break;
for (i = cur[u]; i != -1; i = edge[i].nxt)
if (edge[i].cap != 0 && dep[u] == dep[edge[i].to] + 1)
break;
if (i != -1)
{
cur[u] = i;
stack[top++] = i;
u = edge[i].to;
}
else
{
int min = n;
for (i = head[u]; i != -1; i = edge[i].nxt)
{
if (edge[i].cap == 0)
continue;
if (min > dep[edge[i].to])
{
min = dep[edge[i].to];
cur[u] = i;
}
}
--gap[dep[u]];
++gap[dep[u] = min + 1];
if (u != src)
u = edge[stack[--top]].frm;
}
}
return res;
}
}g;
int main()
{
int T,m,n,i,j,k,x,y,_s,_t,f,_min,_max;
int res;
scanf("%d",&T);
while (T--)
{
_min=inf,_max=-inf;
scanf("%d %d",&n,&m);
g.init(n,m);
for (i=1; i<=n; i++)
{
scanf("%d %d",&x,&y);
if (x<_min) _min=x,_s=i;
if (x>_max) _max=x,_t=i;
}
for (i=0; i<m; i++){
scanf("%d %d %d",&x,&y,&f);
g.addedge(x,y,f);
g.addedge(y,x,f);
}
// printf("s=%d t=%d\n",_s,_t);
if (_s==_t) res=0;else res=g.Sap(_s,_t);
printf("%d\n",res);
}
return 0;
}
1005
数学题,只要确定y,z,就可以二分求出x。所以只要枚举yz就可以, y最多到sqrt(k),z<=31 300ms过
#include <stdio.h>
#include <cmath>
#include <map>
using namespace std;
//#define long long __int64
long long x,y,z,k,tot;
inline long long power(long long a,long long b){
long long ret=1;
for (int i=0;i<b;i++){
ret*=a;
if (ret>k) return (-1);
}
return ret;
}
int main(){
while (scanf("%I64d",&k),k!=0){
tot=0;
for (z=2; z<=30; z++){
for (y=2; y<=int(sqrt(k)) ; y++ ){
// printf("sqrt(%I64d)=%d\n",k,int(sqrt(k)) );
long long l,r,t2=power(y,z);
x=1;
if (t2==-1) break;
// printf("t2=%d ",t2);
l=1;r=sqrt(k);
while (l<=r){
x=(l+r)/2;
int t1=power(x,z);
if (t1==-1){
r=x-1;
}
else
if ( t1+t2+x*y*z>k ){
r=x-1;
}
else if ( t1+t2+x*y*z<k ){
l=x+1;
}
else {
// printf("$ok ");
break;
}
}
if (x>=y) continue;
int t1=power(x,z);
// printf(" t1=%d ",t1);
// printf("x=%d y=%d z=%d\n",x,y,z);
if (t1!=-1)
if (t1+t2+x*y*z ==k){
// printf("x=%I64d y=%I64d z=%I64d\n",x,y,z);
tot++;
}
}
}
printf("%I64d\n",tot);
}
}
1006
DP 多边形剖分的变种,时间O(N^3) 空间O(N^2)
只要确定[i, j]中哪一个是最后出来的,就将区间分成2个子问题,dp[i][j]=MIN(dp[i][j], dp[i][k-1]+dp[k+1][j]+(k-i)*(sum[j]-sum[k])+diaosi[k]*(j-i) );
#include <stdio.h>
#include <string.h>
#define NN 340
#define MIN(x,y) ( ( x ) < ( y )?( x ):( y ) )
int dp[NN][NN],sum[NN],diaosi[NN];
int n,T,i,j,k,l,cas=0;
void Readln(){
memset(dp,7,sizeof(dp));
memset(sum,0,sizeof(sum));
scanf("%d",&n);
for (int i=1;i<=n;i++){
scanf("%d",&diaosi[i]);
sum[i]=sum[i-1]+diaosi[i];
dp[i][i]=0;
dp[i][i-1]=dp[i+1][i]=0;
}
}
void DP(){
for (l=2; l<=n; l++){
for (i=1; i<=n; i++){
j=i+l-1;
for (k=i; k<=j; k++){
dp[i][j]=MIN(dp[i][j],
dp[i][k-1]+dp[k+1][j]+(k-i)*(sum[j]-sum[k])+diaosi[k]*(j-i) );
}
}
}
}
int main(){
scanf("%d",&T);
while ( T-- ){
Readln();
DP();
printf("Case #%d: %d\n",++cas,dp[1][n]);
}
return 0;
}
1007
利用floyd求出最短路,然后忽略不要去的点,用H个点和起点终点组成一个新图,问题即转化为h=15的旅行商问题,dfs吧,500ms+
#include <stdio.h>
#include <string.h>
#define NN 220
struct ZCK{
int num,c,d;
bool used;
}need[NN];
int dis[NN][NN],g[NN][NN];
int visit[NN];
int n,m,money,h;
int fun(int now,int deep){
// printf("now=%d deep=%d money=%d\n",now,deep,money);
int pos=need[now].num;
if (deep==h) {
if ( money-dis[pos][1]>=0 ) return 1;
else return 0;
}
for (int i=1; i<h; i++)
if ( visit[i]==0 ){
int nextpos=need[i].num;
visit[i]=1;
if (money-dis[pos][nextpos]-need[i].d>=0){
money+=(0-dis[pos][nextpos]-need[i].d+need[i].c);
if ( fun(i,deep+1)==1 ) return 1;
money-=(0-dis[pos][nextpos]-need[i].d+need[i].c);
}
visit[i]=0;
}
return 0;
}
void init(){
memset(dis,7,sizeof(dis));
memset(g,7,sizeof(g));
memset(need,0,sizeof(need));
memset(visit,0,sizeof(visit));
}
void floyed(){
int i,j,k;
for (k=1;k<=n;k++)
for (i=1;i<=n;i++)
for (j=1;j<=n;j++)
if (dis[i][k]+dis[k][j]<dis[i][j])
dis[i][j]=dis[i][k]+dis[k][j];
}
int main(){
int T,i,j,k;
int a,b,c;
scanf("%d",&T);
while (T--){
scanf("%d %d %d",&n,&m,&money);
init();
// printf("$$$$%d\n",dis[0][0]);
for (i=1;i<=n;i++) dis[i][i]=g[i][i]=0;
for (i=1;i<=m;i++){
scanf("%d %d %d",&a,&b,&c);
if (g[a][b]>c){
g[a][b]=g[b][a]=c;
dis[a][b]=dis[b][a]=c;
}
}
floyed();
scanf("%d",&h);
for (i=1;i<=h;i++){
scanf("%d %d %d",&need[i].num,&need[i].c,&need[i].d);
}
need[0].num=1,need[0].c=0,need[0].d=0;
visit[0]=1;
h++;
int ret=fun(0,1);
// printf("ret=%d\n",ret);
if (ret==1){
printf("YES\n");
}
else{
printf("NO\n");
}
/* for (i=1;i<=n;i++)
printf("1 to %d = %d\n",i,dis[1][i]);*/
}
return 0;
}
1010
简单题,将字符串转成int类型的数字,直接丢到map里面去+1, 询问的时候直接输出输入的数字在map里的计数就好了。(PS,这题队友做的,我觉得今天写的这个代码简单些)
#include <stdio.h>
#include <string>
#include <string.h>
#include <map>
using namespace std;
int ch[]={2,2,2,3,3,3,4,4,4,5,5,5,6,6,6,
7,7,7,7,8,8,8,9,9,9,9};
int Q[5100];
int tonum(char *s){
int ret=0;
for (int i=0; i<strlen(s);i++)
ret=ret*10+ch[s[i]-'a'];
return ret;
}
int main(){
int T,i,j,k,n,m,tmp,tot;
scanf("%d",&T);
map<int,int> ans;
char buff[100];
while (T--){
ans.clear();
scanf("%d %d",&n,&m);
for (i=0; i<n; i++)
{
scanf("%d",&Q[i]);
}
for (i=0; i<m; i++){
scanf("%s",buff);
tmp=tonum(buff);
ans[tmp]++;
// printf("%s %d\n",buff,tmp);
}
for (i=0; i<n; i++){
printf("%d\n",ans[Q[i]]);
}
}
return 0;
}