Day6 && Day7图论
并查集
A - How Many Answers Are Wrong
题意:
已知区间[1,n],给出m组数据,即[l,r]区间内数据之和为s,求错误数据的数量。
拿到这道题,真的没思路,知道用并查集,但是关于如何定义s迟迟没有思路,就开始了搜文章学习(划水)的历程。
下面就记录一些自己的体会:
1、并查集中路径压缩的过程中如何更新关系域是关键;
2、根据数据定义一些合理的关系(如:集合中的根与集合中的元素的关系),才能对集合进行合并。这里可能会分一些情况讨论,最终应该是可以化简的。
然后放出学习的文章(感谢作者):
里面有关向量的思考和设计很巧妙
#include <cstdio>
#include <algorithm>
#include <cstring>
using namespace std;
const int maxn = ;
int f[maxn];
int sum[maxn]; //记录当前结点到根的距离
int find(int x){
//return x==f[x]?x:find(f[x]);
if(x != f[x]){
int roota = f[x];
f[x] = find(f[x]);
sum[x] += sum[roota];
//x->rootb = x->roota + roota->rootb
}
return f[x];
}
int main(){
//freopen("in.txt","r",stdin);
int n,m;
while(scanf("%d%d", &n, &m) != EOF){
for(int i=; i<=n; i++){
f[i] = i;
sum[i] = ;
}
int ans = ;
while(m--){
int a, b, v;
scanf("%d%d%d", &a, &b, &v);
a--;
//join
int roota = find(a);
int rootb = find(b);
if(roota == rootb){
if(sum[a]-sum[b] != v) ans++;
}else{
f[roota] = rootb;
//定义大的数字是小的数字的根
sum[roota] = -sum[a] + sum[b] + v;
//变换成等式 sum[roota] + sum[a] = sum[b] + v;
//a->roota + roota->rootb == b->rootb + a->b
}
//join
}
printf("%d\n",ans);
}
return ;
}
B - 食物链
摘出上博客中的一句话:
对于集合里的任意两个元素x,y而言,它们之间必定存在着某种联系,因为并查集中的元素均是有联系的(这点是并查集的实质),否则也不会被合并到当前集合中。
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
const int maxn = ;
int f[maxn], relation[maxn];
//relation[i]:i到根的偏移量
int sum;
void init(int n){
for(int i=; i<n; i++){
f[i] = i;
relation[i] = ;
}
sum = ;
}
int find(int x){
if(x != f[x]){
int rootx = f[x];
f[x] = find(rootx);
//路径压缩更新关系域//这是关键1
relation[x] = (relation[x] + relation[rootx]) % ;
}
return f[x];
}
void join(int x, int y, int d){
int rootx = find(x);
int rooty = find(y);
if(rootx != rooty){
f[rooty] = rootx;
relation[rooty] = ( + d- + relation[x] - relation[y]) % ;
//此处d-1题中给出的询问已知条件即0同类,1吃,2被吃
/*先用等式表达:
这里并非简单的加减,实质应该是关系的转移,可以用向量理解
r->rx + x->y = y->ry + ry->rx
====>r[x] + k = r[y] + ry->rx
====>ry->rx = r[x] + k - r[y]
k = d - 1
同理下面两式也得
*/
}else{
if((d==) && (relation[x] != relation[y])){
sum++;
}else if((d==) && ((d-) != (relation[y] - relation[x] + ) % )){
sum++;
}
}
}
int main(){
//freopen("in.txt","r",stdin);
int n, k;
scanf("%d%d", &n, &k);
init(n);
for(int i=; i<k; i++){
int d, x, y;
scanf("%d%d%d",&d, &x, &y);
if(x > n || y > n){
sum++;
}else if((d==) && (x == y)){
sum++;
}else{
join(x, y, d);
}
}
printf("%d\n",sum);
return ;
}
C - A Bug's Life
题意:给定n个bugs,编号依次1、2、……n。它们之间只有雄性和雌性之分,并给定m对交配的情况,根据这m对交配的情况,判断是否有同性恋出现的情况。
Thinking:
定义relation[i]:结点i到根的距离:即相对与根节点的性别。
x,y在同一集合,他们相对根的距离即相对根的性别,而他们又同根,易得x,y的相对性别
x,y不再同一集合,思考向量得关系: y->x + x->rootx = y->rooty + rooty->rootx 其中y->x应为1。
#include <cstdio>
const int maxn = ;
int f[maxn];
int relation[maxn];
bool flag;
void init(int n){
//这里n没有初始完( i < n )导致WA了半天
for(int i=; i<=n; i++){
f[i] = i;
relation[i] = ;
}
}
int find(int x){
if(x != f[x]){
int rootx = f[x];
f[x] = find(rootx);
relation[x] = (relation[rootx] + relation[x]) % ;
}
return f[x];
}
void join(int x, int y){
int rootx = find(x);
int rooty = find(y);
if(rootx == rooty){
if(relation[x] == relation[y]){
flag = true;
}
}else{
/*A了这题后在网上看到很多解法中这里对x,y进行分类,
即 x<y :
f[rooty] = rootx;
relation[rooty] = ((relation[x]+1) + relation[y]) % 2;
x>y :
f[rootx] = rooty;
relation[rootx] = ((relation[y]+1)%2 + relation[x]) % 2;
这里我认为应该可以不需要,因为查找过程中进行了路径压缩
*/
f[rooty] = rootx;
relation[rooty] = ((relation[x]+) - relation[y]) % ;
//这里+由向量y->x + x->rootx = y->rooty + rooty->rootx得应该是-,但%2好像算术上是等价的
//这里我个人认为是减,当然%2时加和减结果一样, 这里留待思考?????
}
}
int main(){
//freopen("in.txt","r",stdin);
int T;
scanf("%d", &T);
for(int t=; t<=T; t++){
int b, inter;
scanf("%d%d",&b, &inter);
init(b);
flag = false;
for(int i=; i<inter; i++){
int x, y;
scanf("%d%d", &x, &y);
if(flag){
continue;
}else{
join(x, y);
}
}
printf("Scenario #%d:\n", t);
if(flag){
printf("Suspicious bugs found!\n\n");
}else{
printf("No suspicious bugs found!\n\n");
}
}
return ;
}
D - Supermarket
并查集,不太想做了,以后补
无向图的割点
E - SPF
题意:一个网络中割点的个数,和割点可以将网络分成几部分。
Thinking:
不用belong记录强连通分量集合的编号,需要加入parent[]记录父节点,child判断子树数量。这是为了分开计算割点是根 和非根的情况。
割点的判断:number[u]<=low[v]即v必须通过u才能访问u的祖先,这里u就是割点,可以参考上面列的第二篇文章。
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
const int maxn = ;
struct Node{
int to;
int next;
}edge[maxn*maxn];
int head[maxn], E, V;
void add_edge(int u, int v){
edge[E].to = v; edge[E].next = head[u]; head[u] = E++;
edge[E].to = u; edge[E].next = head[v]; head[v] = E++;
V = max(max(u,v), V);
}
int size_[maxn];
// 记录删除i结点后的连通分量个数
int low[maxn], number[maxn], parent[maxn];
////Let LOWPT(v) be the smallest vertex in the set ${v}\bigcap { w| v \xrightarrow{*} -\rightarrow w}$
///number[u]为结点u搜索的次序编号
///parent[i]:记录i的父亲结点
bool flag; ///是否有割点存在
int cnt; void dfs(int u){
int child = ;
//记录子树的数量
low[u] = number[u] = ++cnt;
for(int i=head[u]; i!=-; i=edge[i].next){
int v = edge[i].to;
if(!number[v]){
child++;
parent[v] = u;
dfs(v);
///dfs(v)更新low[v]
low[u] = min(low[u], low[v]);
//必须通过u,v才能访问u的祖先number[u]<=low[v]
if((parent[u]==- && child>=) || (parent[u]!=- && number[u]<=low[v])){
/*
child>2保证如果是根节点,将比非根节点少加1
因为如果割点不是根节点,其连通分量要加上其父辈
*/
flag = true;
size_[u]++;
}
}else{
low[u] = min(low[u], number[v]);
}
}
}
void init(){
memset(size_, , sizeof(size_));
memset(number, , sizeof(number));
memset(low, , sizeof(low));
memset(head, -, sizeof(head));
memset(parent, -, sizeof(parent));
E = V = ;
flag = false;
cnt = ;
}
int main(){
// freopen("in.txt","r", stdin);
int cas;
for(int tt=; ;tt++){
init();
//input
int u, v=-;
while(scanf("%d", &u) && u){
scanf("%d", &v);
add_edge(u, v);
}
if(v == -) break;
//input
dfs(V);
printf("Network #%d\n",tt);
if(flag){
for(int i=; i <= V; i++){
if(size_[i] > ){
printf(" SPF node %d leaves %d subnets\n",i,size_[i]+);
}
}
}else{
printf(" No SPF nodes\n");
}
printf("\n");
}
return ;
}
update(2018-08-30):
1、 pre[v]<pre[u]&&v!=f 理解:在无向图中edge(u, f)不是反向边(第一次处理时从后代指向祖先的边),只是树边edge(f, u)的第二次访问。
2、 if(lowv > pre[u]) { u->v is bridge} 这是对桥的判断。
3、在无向连通图G的dfs树中,非根结点u是G的割点当且仅当u存在一个子节点v,使得v及其所有后代都没有反向边连回u的祖先(连回u不算)。
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <vector>
#include <stack>
using namespace std; const int maxn = ;
vector<int> G[maxn]; int iscut[maxn]; int low[maxn], pre[maxn];
//pre:时间戳
//low[u]:u及其后代所能连回的最早祖先的pre值
int cnt, V; int dfs(int u, int f){
int lowu = pre[u] = ++cnt;
int child = ; //子节点数目
for(int i=; i<G[u].size(); i++){
int v = G[u][i];
if(!pre[v]){ //未访问v
child++;
int lowv = dfs(v, u);
lowu = min(lowv, lowu); //用后代low更新low u
if(lowv >= pre[u]){
iscut[u]++;
}
}else if(pre[v]<pre[u] && v!=f){
//v==f无向图,此边不属于反向边,属于树边的二次访问
lowu = min(lowu, pre[v]); //反向边更新u
}
}
if(f< && child==){ //根节点特判
iscut[u] = ;
}
return low[u] = lowu;
}
void add_edge(int a, int b){
G[a].push_back(b); G[b].push_back(a);
V = max(max(a, b), V);
}
void init(){
memset(pre, , sizeof(pre));
memset(iscut, , sizeof(iscut));
for(int i=; i<maxn; i++){ G[i].clear(); }
cnt = ; V = ;
}
int main(){
//freopen("in.txt", "r", stdin);
for(int tt=; ;tt++){
init();
int u, v=-;
while(scanf("%d", &u) && u){
scanf("%d", &v);
add_edge(u, v);
}
if(v == -) break;
dfs(V, -);
printf("Network #%d\n", tt);
bool flag = true;
for(int i=; i<=V; i++){
if(iscut[i]){
printf(" SPF node %d leaves %d subnets\n", i, iscut[i]+);
flag = false;
}
}
if(flag){
printf(" No SPF nodes\n");
}puts("");
}
return ;
}
有向图的强连通分量
完成了一个Tarjan的算法实现,第一次写,有待优化。
F - Proving Equivalences
题意:给一个有向图,试求添加多少条边可以使该图成为强连通图。
Thinking:
要利用DAG的性质,则需要用Tarjan算法缩点,将有向图转为DAG。
至于添加多少条边,可以这样想,怎样操作能构成最大环,即将DAG头尾相连即可。即求入度和出度的max();
需要特判强连通分量个数为一的情况如(1,2)(2,1),则不需要加边。
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <stack>
using namespace std;
const int maxn = ;
struct Node{
int to;
int next;
}edge[maxn * ];
int head[maxn],cnt;
stack<int> S;
int low[maxn], number[maxn];
int belong[maxn], scc;
//保存每个点属于的强连通集合的编号; 强连通分量编号最大值(即个数
void add_edge(int u, int v){
edge[++cnt].to = v;
edge[cnt].next = head[u];
head[u] = cnt;
}
void dfs(int u){
S.push(u);
number[u] = low[u] = ++cnt;
for(int i = head[u]; i!=-; i = edge[i].next){
int v = edge[i].to;
if(!number[v]){
dfs(v);
low[u] = min(low[u], low[v]);
}else if(!belong[v]){
low[u] = min(low[u], number[v]);
}
}
if(number[u] == low[u]){
scc++;
int v;
do{
v = S.top(), S.pop();
belong[v] = scc;
}while(u != v);
}
}
int in[maxn], out[maxn];
void init(){
cnt = scc = ;
memset(head, -, sizeof(head));
memset(number, , sizeof(number));
memset(low, , sizeof(low));
memset(in, , sizeof(in));
memset(out, , sizeof(out));
memset(belong, , sizeof(belong));
while(!S.empty()) S.pop();
}
int main(){
//freopen("in.txt", "r", stdin);
int T;
scanf("%d", &T);
while(T--){
init();
int n, m;
scanf("%d%d", &n, &m);
for(int i=; i<m; i++){
int u, v;
scanf("%d%d", &u, &v);
add_edge(u, v);
}
cnt = ;
for(int i=; i<=n; i++){
if(!number[i]){
dfs(i);
}
}
if(scc == ){
printf("0\n");
continue;
}
for(int i=; i<=n; i++){
for(int j=head[i]; j!=-; j=edge[j].next){
int v = edge[j].to;
if(belong[v] != belong[i]){
in[belong[v]]++;
out[belong[i]]++;
}
}
}
int ans1 = , ans2 = ;
for(int i=; i<=scc; i++){
if(!out[i]) ans1++;
if(!in[i]) ans2++;
}
printf("%d\n",max(ans1, ans2));
}
return ;
}
#include <bits/stdc++.h>
using namespace std; const int maxn = ;
vector<int> G[maxn];
stack<int> S;
int pre[maxn], lowlink[maxn], sccno[maxn], dfs_clock, scc_cnt;
//sccno[i]: i所在的SCC编号
void dfs(int u){
pre[u] = lowlink[u] = ++dfs_clock;
S.push(u);
for(int i=; i<G[u].size(); i++){
int v = G[u][i];
if(!pre[v]){
dfs(v);
lowlink[u] = min(lowlink[u], lowlink[v]);
}else if(!sccno[v]){
lowlink[u] = min(lowlink[u], pre[v]);
}
}
if(lowlink[u] == pre[u]){
scc_cnt++;
while(true){
int x = S.top(); S.pop();
sccno[x] = scc_cnt;
if(x == u) break;
}
}
}
int find_scc(int n){
dfs_clock = scc_cnt = ;
memset(sccno, , sizeof(sccno));
memset(pre, , sizeof(pre));
for(int i=; i<n; i++){
if(!pre[i]) dfs(i);
}
}
int in[maxn], out[maxn]; int main(){
//freopen("in.txt", "r", stdin);
int t; scanf("%d", &t);
while(t--){
int n, m; scanf("%d%d", &n, &m);
for(int i=; i<n; i++) G[i].clear();
for(int i=; i<m; i++){
int a, b; scanf("%d%d", &a, &b); a--, b--;
G[a].push_back(b);
}
find_scc(n);
// 对缩点后的DAG入度和出度计算
//in[i]:i的入度为0
for(int i=; i<=scc_cnt; i++) in[i] = out[i] = ;
for(int u=; u<n; u++){
for(int i=; i<G[u].size(); i++){
int v = G[u][i];
if(sccno[u] != sccno[v]) in[sccno[v]] = out[sccno[u]] = ;
//u,v对应的出入度不为0
}
}
//
int a = , b = ;
for(int i=; i<=scc_cnt; i++){
if(in[i]) a++;
if(out[i]) b++;
}
int ans = max(a, b);
if(scc_cnt == ) ans = ;
printf("%d\n", ans);
}
return ;
}
G - The Largest Clique
题意:给一个有向图G,求一个结点数最大的结点集(任意两点相互可达)。
Targan缩点 + DAG上的最长路。 给一个含圈的有向图,求最长路。
#include <bits/stdc++.h>
using namespace std; const int maxn = ;
vector<int> G[maxn], mp[maxn];
stack<int> S;
int pre[maxn], lowlink[maxn], sccno[maxn], dfs_clock, scc_cnt;
//sccno[i]: i所在的SCC编号
void dfs(int u){
pre[u] = lowlink[u] = ++dfs_clock;
S.push(u);
for(int i=; i<G[u].size(); i++){
int v = G[u][i];
if(!pre[v]){
dfs(v);
lowlink[u] = min(lowlink[u], lowlink[v]);
}else if(!sccno[v]){
lowlink[u] = min(lowlink[u], pre[v]);
}
}
if(lowlink[u] == pre[u]){
scc_cnt++;
int x;
do{
x = S.top(); S.pop();
sccno[x] = scc_cnt;
}while(x != u);
}
}
void find_scc(int n){
dfs_clock = scc_cnt = ;
memset(sccno, , sizeof(sccno));
memset(pre, , sizeof(pre));
for(int i=; i<n; i++){
if(!pre[i]) dfs(i);
}
}
int size_[maxn], d[maxn]; //DAG上的最长距离
int dp(int u) {
if(d[u] >= ) return d[u];
d[u] = size_[u];
for(int i = ; i < mp[u].size(); i++){
int v = mp[u][i];
d[u] = max(d[u], dp(v) + size_[u]);
}
return d[u];
}
void build(int n){
for(int i=; i<=scc_cnt; i++) mp[i].clear();
memset(size_, , sizeof(size_));
for(int i=; i<n; i++) size_[sccno[i]]++;
for(int i=; i<n; i++){
for(int j=; j<G[i].size(); j++){
int v = G[i][j];
if(sccno[i] != sccno[v]){
mp[sccno[i]].push_back(sccno[v]);
}
}
}
}
int main(){
// freopen("in.txt", "r", stdin);
int t; scanf("%d", &t);
while(t--){
int n, m; scanf("%d%d", &n, &m);
for(int i=; i<n; i++) G[i].clear();
for(int i=; i<m; i++){
int a, b; scanf("%d%d", &a, &b); a--; b--;
G[a].push_back(b);
} find_scc(n); build(n); int ans = ;
memset(d, -, sizeof(d));
for(int i=; i<=scc_cnt; i++){
ans = max(ans, dp(i));
}
printf("%d\n", ans);
}
return ;
}
无向图的双连通分量
K - Knights of the Round Table(uva 3523)
题意:n个骑士举行会议,每次圆桌会议至少三人,且骑士数目为奇数,相互憎恨的骑士不能再相邻位置,问多少个骑士不能参加会议。
二分图 + BCC
建图:两个骑士可以相邻,则建一条无向边。
求不在任何一个简奇圈上的结点个数。
简单圈上的所有结点必然属于同一个双连通分量;二分图没有奇圈。
#include <bits/stdc++.h>
using namespace std;
const int maxn = ; struct edge{
int u, v;
edge(int a, int b) : u(a), v(b) {}
};
int pre[maxn], iscut[maxn], bccno[maxn], dfs_clock, bcc_cnt;
//bccno[i]=x:第i个顶点属于第x个点-双连通分量
vector<int> G[maxn], bcc[maxn];
//bcc[i]: 编号为i的点-双连通分量的所有结点
stack<edge> S; int dfs(int u, int f){
int lowu = pre[u] = ++dfs_clock;
int child = ;
for(int i=; i<G[u].size(); i++){
int v = G[u][i];
edge e = (edge){u, v};
if(!pre[v]){
S.push(e);
child++;
int lowv = dfs(v, u);
if(lowv >= pre[u]){
iscut[u]++;
bcc_cnt++; bcc[bcc_cnt].clear();
while(true){
edge x = S.top(); S.pop();
if(bccno[x.u] != bcc_cnt){
bcc[bcc_cnt].push_back(x.u);
bccno[x.u] = bcc_cnt;
}
if(bccno[x.v] != bcc_cnt){
bcc[bcc_cnt].push_back(x.v);
bccno[x.v] = bcc_cnt;
}
if(x.u == u && x.v == v){
break;
}
}
}
}else if(pre[v] < pre[u] && v != f){
S.push(e);
lowu = min(lowu, pre[v]);
}
}
if(f < && child==) iscut[u]=;
return lowu;
} void find_bcc(int n){
memset(pre, , sizeof(pre));
memset(iscut, , sizeof(iscut));
memset(bccno, , sizeof(bccno));
dfs_clock = bcc_cnt = ;
for(int i=; i<n; i++){
if(!pre[i]) dfs(i, -);
}
}
int color[maxn];
bool odd[maxn];
bool bipartite(int u, int b){
for(int i=; i<G[u].size(); i++){
int v = G[u][i];
if(bccno[v] != b) continue;
if(color[v] == color[u]){
return false;
}
if(!color[v]){
color[v] = - color[u];
if(!bipartite(v, b)) return false;
}
}
return true;
}
int A[maxn][maxn]; int main(){
//freopen("in.txt", "r", stdin);
int kase = , n, m;
while(scanf("%d%d", &n, &m) != EOF && n){
for(int i=;i<n;i++)G[i].clear();
memset(A, , sizeof(A)); for(int i=;i<m;i++){
int a,b; scanf("%d%d",&a, &b); a--,b--;
A[a][b] = A[b][a] = ;
}
for(int i=; i<n; i++){
for(int j=i+; j<n; j++){
if(!A[i][j]) G[i].push_back(j), G[j].push_back(i);
}
} find_bcc(n); memset(odd, , sizeof(odd));
for(int i=; i<=bcc_cnt; i++){
for(int j=; j<bcc[i].size(); j++){ //同一个BBC内统一编号
bccno[bcc[i][j]] = i;
}
int u = bcc[i][]; memset(color, , sizeof(color));
color[u] = ;
if(!bipartite(u, i)){ //不是二分图,标记为奇圈
for(int j=; j<bcc[i].size(); j++){
odd[bcc[i][j]] = true;
}
}
}
int ans = n;
for(int i=; i<n; i++) if(odd[i]) ans--;
printf("%d\n", ans);
}
return ;
}
Day6 && Day7图论的更多相关文章
- ZROI 暑期高端峰会2019 总结
FBI Warning:以下博客含有 FBI Warning 的都是包含大量人类本质之一的. 前几天听课: Day1 组合计数 Day1 序列数据结构 Day2 线性代数 Day3 图论 Day3 字 ...
- 【Beta版本】七天冲刺——日志集合贴
No Bug 031402401鲍亮 031402402曹鑫杰 031402403常松 031402412林淋 031402418汪培侨 031402426许秋鑫 Day1 Day2 Day3 Day ...
- 软件工程(FZU2015)赛季得分榜,第11回合(beta冲刺+SE总结)
目录 第一回合 第二回合 第三回合 第四回合 第五回合 第6回合 第7回合 第8回合 第9回合 第10回合 第11回合 增补作业 积分规则 积分制: 作业为10分制,练习为3分制:alpha30分:b ...
- 【Alpha版本】十天冲刺——日志集合贴
No Bug 031402401鲍亮 031402402曹鑫杰 031402403常松 031402412林淋 031402418汪培侨 031402426许秋鑫 Day1 Day2 Day3 Day ...
- 一起买beta版本文档报告汇总
一起买beta版本文档报告汇总 031402401鲍亮 031402402曹鑫杰 031402403常松 031402412林淋 031402418汪培侨 031402426许秋鑫 一.Beta版本冲 ...
- 一起买Beta版本系列文档
一起买beta版本文档报告汇总 031402401鲍亮 031402402曹鑫杰 031402403常松 031402412林淋 031402418汪培侨 031402426许秋鑫 一.Beta版本冲 ...
- 报错:对象必须实现 IConvertible;以分隔符进行分割链接concat_ws的使用方法;mysql数据类型转换cast,convert
错误故障,mysql 服务器上用 concat_ws 函数,连接了一串数字,最后 服务器返回的字段就变成了一个 byte ,而我们想要的类型是 string 类型,那么转换的时候,就报错了. 正确 ...
- 软件工程(FZU2015) 赛季得分榜,第11回合(beta冲刺+SE总结)
SE_FZU目录:1 2 3 4 5 6 7 8 9 10 11 12 13 积分规则 积分制: 作业为10分制,练习为3分制:alpha30分:beta30分 团队项目分=团队得分+个人贡献分 个人 ...
- Python内置的操作系统模块(os)与解释器交互模块(sys)
Python内置的操作系统模块(os)与解释器交互模块(sys) 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 本片博客只介绍Python调用操作系统的模块即os模块,以及Pyth ...
随机推荐
- c++字符和字符串转整数类型及大小端
在网络传输中,很多数据都是按字节传递而不是字符串.最近就遇到了这个问题,在刚开始学c语言时都没有问题,可能太久不用了,记录一下 在报中文,用2个字节hex码来表示报文正文长度,什么是hex码呢 就是1 ...
- mybatis总体分析
Mybatis是一个半orp框架,说是半,也就是不完全是,还有很多地方是需要开发人员完成的.发现很多互联网公司使用Mybatis,而不是hibernate.应该是因为Mybatis不但有orp的优势, ...
- springboot打包后静态资源webapp文件夹无法打包进去
1.如下图的目录结构 webapp 文件夹和resources 文件夹同级.使用mvn clean install 打包过后项目启动访问,静态资源页面404. 2.原因,springboot 打包时候 ...
- pdf缩略图上传控件
一. 功能性需求与非功能性需求 要求操作便利,一次选择多个文件和文件夹进行上传:支持PC端全平台操作系统,Windows,Linux,Mac 支持文件和文件夹的批量下载,断点续传.刷新页面后继续传输. ...
- NTT 练习
一 . Rikka with Subset 题目: http://acm.hdu.edu.cn/showproblem.php?pid=5829 参考 https://blog.csdn.net/ ...
- P4981 父子 Cayley公式
CayleyCayley公式的定义是这样的,对于n个不同的节点,能够组成的无根树(原来是无向连通图或者是有标志节点的树)的种数是n^(n-2)种.(这里让大家好理解一点,就写成了无根树,其实应该是一样 ...
- UBUNTU 15.10 CAFFE安装教程(测试可用)
转帖:https://github.com/BVLC/caffe/wiki/Ubuntu-15.10-Installation-Guide Ubuntu 15.10 have been release ...
- HFUUOJ1023 闷声发大财 概率dp
题意 xyq有\(n\)个骰子,第\(i\)个骰子有\(a_i\)面,每次xyq都会把\(n\)个骰子搞一遍,其中的最小值作为结果,问最终结果的期望\(\mod (10^9+7 )\). 分析 lfx ...
- 项目部署中,tomcat报java.lang.OutOfMemoryError: PermGen space
原因: PermGen space的全称是Permanent Generation space,是指内存的永久保存区域,这块内存主要是被JVM存放Class和Meta信息的,Class在被Loader ...
- codeforces666A
Reberland Linguistics CodeForces - 666A First-rate specialists graduate from Berland State Institute ...