bool dfs(int v,int c)
{
color[v]=c;
for (int i=0; i<G[v].size(); i++)
if (color[G[v][i]]==c)
return 0;
if (color[G[v][i]]==0&& !dfs(G[v][i],-c))
return 0;
return 1;
}
for (i=1; i<=n; i++)
if (color[i]==0)
if (dfs(i,1))
{
printf("No\n");
return 0;
}
printf("Yes\n");
dijkstra
memset(d,0x3f,sizeof(d));
d[s]=0;
while (1)
{
int k=-1;
for (i=1; i<=n; i++)
if (!v[i] &&(k==-1||d[i]<d[k]))
k=i;
if (k==-1)
break;
v[k]=1;
for (i=1; i<=n; i++)
d[i]=min(d[i],d[i]+cost[k][i]);
}
dijkstra
memset(d,0x3f,sizeof(d));
d[s]=0;
q.push(P(0,s));
while (q.size())
{
int x=q.front().first,y=q.front().second;
q.pop();
if (v[y])
contine;
v[y]=1;
for (i=0; i<G[y].size(); i++)
{
int k=G[y][i].t,k1=G[y][i].w;
if (d[k]>d[x]+k1)
{
d[k]=d[x]+k1;
q.push(P(d[k],k));
}
}
}
dijkstra
memset(d,0x3f,sizeof(d));
d[s]=0;
while (1)
{
int k=-1;
for (i=1; i<=n; i++)
if (!v[i] &&(k==-1||d[i]<d[k]))
k=i;
if (k==-1)
break;
v[k]=1;
for (i=1; i<=n; i++)
{
d[i]=min(d[i],d[i]+cost[k][i]);
per[i]=k;
}
}
vector<int> getpath(int t)
{
vector<int>path;
for (; t; t=pre[t])
path.push_back(t);
reserve(path.begin(),path.end());
return path;
}
priority<P,vector<P>,greater<P> >q'
memset(dist,0x3f,sizeof(dist));
memset(dist2,0x3f,sizeof(dist2));
dist[0]=0;
q.push(P(0,0));
while (q.size())
{
P p=q.top();
q.pop();
int v=p.second,d=p.first;
if (vis[v])
continue;
vis[v]=1;
for (int i=0; i<G[v].size(); i++)
int x=G[v][i].t;
d2=d+y=G[v][i].w;
if (dist[x]>d2)
{
swap(dist[x],d2);
q.push(P(dist[x],x));
}
if (dist2[x]>d2&&dist[x]<d2)
{
dist2[x]=d2;
q.push(P(dist2[x],x));
}
}
printf("%d\n",dist2[n-1]);
exgcd(int a,int b,int &d,int &x,int &y)
{
if (b==0)
{
d=a;
x=1;
y=0;
return;
}
else
{
exgcd(b,a%b,d,y,x);
y=y-x*a/b
}
}
//判断素数
bool is_prime(int n)
{
for (i=2; i*i<=n; i++)
if (n%i==0)
return 0;
return n!=1;
}
//求因数
vector<int>divsior(int n)
{
vector<int>res;
for (i=1; i*i<=n; i++)
if (n%i==0)
{
res.push_back(i);
if (i!=n/i)
res.push_back(n/i);
}
return res;
}
//整数分解
map<int,int>prime_factor(int n)
{
map<int,int>res;
for (i=2; i*i<=n; i++)
while (n%i==0)
{
res[i]++;
n=n/i;
}
}
p[1]=1;
p[0]=1;
for (i=2; i<=n; i++)
if (p[i]==0)
{
prime[l++]=i;
for (j=i+i; j<=n; j+=i)
p[j]=1;
}
is_prime[i-a]=1 i是素数
for (i=0; (ll)i*i<=b; i++)
is_prime_small[i]=1;
for (i=0; i<b-a; i++)
is_prime[i-a]=1;
for (i=2; (ll)i*i<b; i++)
if (is_prime_small[i])
{
for (j=i+i; (ll)j*j<b; j+=i)
is_prime_small[j]=0;
for (j=max(2LL,(a+i-1)/i)*i; j<b; j+=i)
is_prime[j-a]=0;
}
sort(v1,v1+n);
sort(v2,v2+n);
for (i=0;i<n;i++)
ans+=v1[i]*v2[n-i-1];
输出
0
int a[] // a[i]表示第i行最后出现的1的位置——1~n-1
for (i=0; i<n; i++)
{
a[i]=-1; // 如果第i行不含1的话,就当作-1
for (j=0; j<n; j++)
if (M[i][j]==1)
a[i]=j;
}
for (i=0; i<n; i++)
{
int pos = -1; // 要移动到第i行的行
for (j=i; j<n; j++)
if (a[j]<=i)
{
pos=j;
break;
}
// 完成交换
for (j=pos;j>i;j--)
{
swap(a[j], a[j - 1]);
ans++;
}
}
printf("%d\n",ans);
dp[i][j]表示的是,将从A[i]号囚犯到A[j]号囚犯(不含两端的囚犯)的连续部分里的
所有囚犯都释放时,所需的最少金币总数。
a[0]=0;
a[Q+1]=p+1;
for (i=0; i<=Q; i++)
dp[i][i+1]=0;
for (l=2; l<=Q+1; l++)
{
for (i=0; i<=Q+1; i++)
{
j=i+l;
if (j>Q+1) break;
t=INF;
for (k=i+1; k<j; k++)
{
t=min(t,dp[i][k]+dp[k][j]);
}
dp[i][j]=t+a[j]-a[i]+2;
}
}
printf("%d\n",dp[0][Q+1]);
为了更方便地处理两端的情况,我们把左端当成0号囚犯,右端当成Q+1号囚犯.
这样,dp[0][Q+1]就是答案。
int M,X;
double P;
double dp[2][(1 << MAX_M) + 1];
int n=1<<M;
double *prv=dp[0],*nxt=dp[1];
memset(prv,0,sizeof(double)*(n+1));
prv[n]=1.0;
for (r=0; r<M; r++)
{
for (i=0; i<=n; i++)
{
int k=min(i,n-i);
double t=0;
for (int j=0; j<=k; j++)
{
t=max(t,p*prv[i+j]+(1-p)*prv[i-j]);
}
nxt[i]=t;
}
swap(prv,nxt);
}
int i=(ll)X*n/1000000;
printf("%.6f\n",prv[i]);