• 沒有找到結果。

2.1ConvexHull 22.CombinationalGemoetry 1.2MersennePrime 3.2BipartiteMatching 1.1LinearSieve 11.MathematicalRelated 3.1ArticulationPoint 33.GraphTheory 2.2ExtendGCD Contents

N/A
N/A
Protected

Academic year: 2022

Share "2.1ConvexHull 22.CombinationalGemoetry 1.2MersennePrime 3.2BipartiteMatching 1.1LinearSieve 11.MathematicalRelated 3.1ArticulationPoint 33.GraphTheory 2.2ExtendGCD Contents"

Copied!
6
0
0

加載中.... (立即查看全文)

全文

(1)

Contents

1 1. Mathematical Related 1

1.1 Linear Sieve . . . 1

1.2 Mersenne Prime . . . 1

2 2. Combinational Gemoetry 1 2.1 Convex Hull . . . 1

2.2 Extend GCD . . . 1

3 3. Graph Theory 1 3.1 Articulation Point . . . 1

3.2 Bipartite Matching . . . 1

3.3 Dijkstra . . . 2

3.4 Kruskal . . . 2

3.5 Min Cost Max Flow . . . 2

3.6 SCC-Tarjan . . . 2

3.7 Second Order MST . . . 3

3.8 Second Order Shortest Path . . . 3

4 4. String Matching 3 4.1 AC Automaton . . . 3

4.2 KMP . . . 4

4.3 Sux Array . . . 4

4.4 Trie . . . 4

5 5. STL 4 5.1 STL Heap . . . 4

5.2 using STL . . . 5

6 6. Other 5 6.1 Heap . . . 5

6.2 Minimun Encloseing Circle . . . 5

6.3 Rectangle Cover Area . . . 6

1 1. Mathematical Related

1.1 Linear Sieve

/*

* find prime numbers by linear sieve

* MAX is the maximum range

* p stores prime numbers

* f stores the primer number that sieved the number

* t is the amount of prime numbers

*/

#define MAX 65521

#define HLF MAX/2

#define PRI MAX/5

int p[PRI],f[MAX+1]={};

int linear_sieve(){

int t=0,i,j,n,m;

for (i=2;i<=HLF;++i){

if (!f[i])p[t++]=i;

for (j=0;j<=t&&i*p[j]<=MAX;++j){

f[i*p[j]]=p[j];

if (p[j]==f[i])break;

} }

for (;i<=MAX;++i){

if (!f[i])p[t++]=i;

}

return t;

}

1.2 Mersenne Prime

int Mersenne_prime[]={

2,3,5,7,13,17,19,31,61,89,107,127,521,607, 1279,2203,2281,3217,4253,4423,9689,9941,11213, 19937,21701,23209,44497,86243

}

2 2. Combinational Gemoetry

2.1 Convex Hull

struct point{ __int64 x, y; } p[100000], s1[100000], s2 [100000];

bool operator <(const point &a, const point &b){ return a.y

==b.y?a.x<b.x:a.y<b.y; }

__int64 cross(point a, point b, point c){ return (b.x-a.x)*(

c.y-a.y)-(c.x-a.x)*(b.y-a.y); } int main(){

int t1=0, t2=0, i, n;

scanf("%d", &n);

for(i = 0; i < n; i++) scanf("%I64d%I64d", &p[i].x, &p[i].

y);

sort(p, p+n);

for(i = 0; i < n; i++){

while(t1>1&&cross(s1[t1-2], s1[t1-1], p[i])>=0) t1--;

while(t2>1&&cross(s2[t2-2], s2[t2-1], p[i])<=0) t2--;

s1[t1++] = p[i];

s2[t2++] = p[i];

}

printf("%d\n", t1+t2-2);

return 0;

}

2.2 Extend GCD

int ext_gcd(int a, int b, int p, int q, int r, int s){

if(b==0)return p;

return ext_gcd(b, a%b, r, s, p-r*(a/b), q-s*(a/b)) }

3 3. Graph Theory

3.1 Articulation Point

#include<iostream>

#include<vector>

#define N 10001 using namespace std;

vector<int> v[N];

int dfn[N], low[N], ind, n, m, cnt;

bool ap[N];//the point which is AP void DFS(int i, int from){

int ch=0;

dfn[i]=low[i]=++ind;

for(vector<int>::iterator it=v[i].begin(); it!=v[i].end();

it++){

if(*it==from);

else if(dfn[*it]==-1){

DFS(*it, i); ch++;

if(low[*it]<low[i]) low[i]=low[*it];

if((from!=-1&&low[*it]>=dfn[i])||(from==-1&&ch>1)) cnt +=(ap[i]=1);

}

else if(dfn[*it]<low[i]) low[i]=dfn[*it];

} }

int main(){

int i, j, t=0;

while(scanf("%d%d", &n, &m), n|m){

cnt=ind=0;

for(i=1; i<=n; i++){

v[i].clear();

dfn[i]=low[i]=-1; ap[i]=0;

}

while(m--){

scanf("%d%d", &i, &j);

v[i].push_back(j);

v[j].push_back(i);

}

for(i=0; i<=n; i++)

if(dfn[i]==-1) DFS(i, -1);

printf("Case #%d:%d\n", ++t, cnt);

}

return 0;

}

3.2 Bipartite Matching

#include<iostream>

#define N 501 using namespace std;

bool map[N][N], vy[N];

int mx[N], my[N], n, m;

bool DFS(int i){

for(int j=1; j<=n; j++) if(map[i][j]&&!vy[j]){

vy[j]=1;

if(my[j]==-1||DFS(my[j])){

my[j]=i; mx[i]=j;

return 1;

} } return 0;

}

int main(){

int i, j, ans=0;

memset(mx, -1, sizeof(mx));

memset(my, -1, sizeof(my));

scanf("%d%d", &n, &m);

1

(2)

while(m--){

scanf("%d%d", &i, &j);

map[i][j]=1;

}

for(i=1; i<=n; i++){

memset(vy, 0, sizeof(vy));

ans+=DFS(i);

}

printf("%d\n", ans);

return 0;

}

3.3 Dijkstra

#include<iostream>

#define INF 1000000000

#define MAX 9 using namespace std;

int main(){

int dis[MAX][MAX], n, i, j, k, a, b, d, path[MAX], parent[

MAX], min, w;

bool visit[MAX];

while(scanf("%d", &n)){

memset(visit, 0, sizeof(visit));

memset(parent, 0, sizeof(parent));

for(i = 0; i < MAX; i++){

path[i] = INF;

for(j = 0; j < MAX; j++) dis[i][j] = INF;

}

while(n--){

scanf("%d%d%d", &a, &b, &d);

dis[a][b] = d;

}

visit[0] = 1;

path[0] = 0;

for ( i = 0; i < MAX; i++ ) path[i] <?= dis[0][i];

k = MAX;

while(--k){

min = INF;

for(i = 0; i < MAX; i++) {

if ( !visit[i] && path[i] < min ) { min = path[i];

w = i;

} }

printf("now choice is %d\n",w);

visit[w] = 1;

for ( i = 0; i < MAX; i++ ) path[i] <?= path[w] + dis[w][i];

}

for ( i = 0; i < MAX; i++ )

printf("dist to %d is %d\n",i,path[i]);

}

return 0;

}

3.4 Kruskal

//Kruskal

#include<iostream>

using namespace std;

struct p2p{ int a, b, cost; };

bool operator <(const p2p &x, const p2p &y){return x.cost <

y.cost;}

p2p p[1000000];

int from[10001], now, ans;

int find(int x){ return x == from[x] ? x : from[x] = find(

from[x]); }

void Union(int x, int y){ from[find(x)] = find(y); } int main(){

int n, m, i, t, tmp;

while(scanf("%d%d", &n, &m), n){

for(i = 0; i < m; i++)

scanf("%d%d%d", &p[i].a, &p[i].b, &p[i].cost);

for(i = 1; i <= n; i++) from[i] = i;

sort(p, p+m);

t = n-1, ans = now = 0;

while(t && now < m){

if(from[find(p[now].a)] != from[find(p[now].b)]){//

different parts, union.

ans += p[now].cost;

Union(p[now].a, p[now].b);

t--;

} now++;

}

for(i = 2, find(1); i <= n; i++) if(find(i) != from[i-1]){

ans = -1;

break;

}

printf("%d\n", ans);

}

return 0;

}

3.5 Min Cost Max Flow

#include<iostream>

#include<queue>

#define INF 2147483647 using namespace std;

int n, m, d, r, i, j, now, ans, f, c, flow[202][202], cost [202][202], from[202], dis[202], a[101], b[101];

bool inq[202];

queue<int> q;

int main(){

while(~scanf("%d%d%d", &n, &d, &r)){

memset(flow, 0, sizeof(flow));

memset(cost, 0, sizeof(cost));

for(i=1; i<=n; i++) scanf("%d", a+i);

for(i=1; i<=n; i++) scanf("%d", b+i);

for(i=1, m=n+n+1, ans=0; i<=n; i++){

flow[0][i]=flow[n+i][m]=1;

for(j=1; j<=n; j++){

flow[i][n+j]=1;

if(a[i]+b[j]>d){

cost[i][n+j]=a[i]+b[j]-d;

cost[n+j][i]=-cost[i][n+j];

} } }

while(1){

memset(from, -1, (m+1)*4);

fill(dis, dis+m+1, INF);

q.push(0); inq[0]=1; dis[0]=0;

while(!q.empty()){

now=q.front(); q.pop(); inq[now]=0;

for(i=0; i<=m; i++)

if(flow[now][i]>0&&dis[now]+cost[now][i]<dis[i]){

dis[i]=dis[now]+cost[now][i];

from[i]=now;

if(!inq[i]){ q.push(i); inq[i]=1; } }

}

if(from[m]==-1) break;

for(i=m, f=INF, c=0; i; i=from[i]){

f<?=flow[from[i]][i];

c+=cost[from[i]][i];

}

for(i=m; i; i=from[i]){

flow[from[i]][i]-=f;

flow[i][from[i]]+=f;

} ans+=f*c;

}

printf("%d\n", ans*r);

}

return 0;

}

3.6 SCC-Tarjan

#include<iostream>

#include<vector>

#define N 100000 using namespace std;

vector<int> v[N+1];

int stack[N+1], top, tot, dfn[N+1], low[N+1], m, n, num[N +1], cnt;

bool ins[N+1];

void tarjan(int i){

dfn[i]=low[i]=++tot;

stack[top++]=i;

ins[i]=1;

for(vector<int>::iterator it=v[i].begin(); it!=v[i].end();

it++){

if(!dfn[*it]){

tarjan(*it);

if(low[*it]<low[i]) low[i]=low[*it];

}

else if(ins[*it]&&low[*it]<low[i]) low[i]=low[*it];

}

if(dfn[i]==low[i]){

cnt++;

do{

ins[stack[--top]]=0;

num[cnt]++;

//belong[stack[top]]=bcnt;

}while(stack[top]!=i);

2

(3)

} }

int main(){

int i, j;

while(~scanf("%d%d", &n, &m)){

for(i = 1; i <= n; i++){

v[i].clear();

ins[i]=0, num[i]=dfn[i]=0;

}

top=tot=cnt=0;

while(m--){

scanf("%d%d", &i, &j);

v[i].push_back(j);

}

for(i = 1; i <= n; i++) if(!dfn[i]) tarjan(i);

sort(num+1, num+cnt+1);

printf("%d", num[1]);

for(i = 2; i <= cnt; i++) printf(" %d", num[i]);

puts("");

}

return 0;

}

3.7 Second Order MST

#include<iostream>

#include<vector>

#define N 1001 using namespace std;

struct Edge{ int a, b; long long c; bool used;} e[500000];

int from[N], n, m;

long long big[N][N], ans=0, ans2=LLONG_MAX;

vector<int> v[N];

bool vis[N];

inline bool operator <(const Edge a, const Edge b){return a.

c<b.c;}

int find(int x){return x==from[x]?x:from[x]=find(from[x]);}

void DFS(int s, int n, int b){

vis[n]=1;

big[s][n]=b;

for(vector<int>::iterator it=v[n].begin(); it!=v[n].end();

it++)

if(!vis[*it]) DFS(s, *it, b>?big[n][*it]);

vis[n]=0;

}

int main(){

int i, j;

scanf("%d%d", &n, &m);

for(i=1; i<=n; i++) from[i]=i;

for(i=1; i<=m; i++)

scanf("%d%d%I64d", &e[i].a, &e[i].b, &e[i].c);

sort(e+1, e+m+1);

for(i=j=1; i<n&&j<=m; i++){

while(j<=m&&find(e[j].a)==find(e[j].b)) j++;

if(j>m) break;

e[j].used=1;

v[e[j].a].push_back(e[j].b);

v[e[j].b].push_back(e[j].a);

big[e[j].a][e[j].b]=big[e[j].b][e[j].a]=e[j].c;

ans+=e[j].c;

from[find(e[j].a)]=find(e[j].b);

}

if(i<n) puts("-1 -1");

if(m==n-1) printf("%I64d -1\n", ans);

else{

for(i=1; i<=n; i++) DFS(i, i, 0);

for(i=1; i<=m; i++)

if(!e[i].used&&ans2>e[i].c-big[e[i].a][e[i].b]) ans2=e [i].c-big[e[i].a][e[i].b];

printf("%I64d %I64d\n", ans, ans+ans2);

} }

3.8 Second Order Shortest Path

#include<iostream>

#include<queue>

#define N 100

#define INF 2147483647 using namespace std;

int n, m, i, j, k, s, t, now, from[N], to[N], map[N][N], dis , ans;

bool inq[N];

queue<int> q;

int main(){

while(~scanf("%d%d", &n, &m)){

for(i=0; i<n; i++){

from[i]=to[i]=INF;

memset(map[i], 0, n*4);

}

while(m--){

scanf("%d%d%d",&i, &j, &k);

map[i][j]=map[j][i]=k;

}

scanf("%d%d", &s, &t);

q.push(s), inq[s]=1, from[s]=0;

while(!q.empty()){

now=q.front(), q.pop(), inq[now]=0;

for(i=0; i<n; i++)

if(map[now][i]&&from[now]+map[now][i]<from[i]){

from[i]=from[now]+map[now][i];

if(!inq[i]) q.push(i), inq[i]=1;

} }

q.push(t), inq[t]=1, to[t]=0;

while(!q.empty()){

now=q.front(), q.pop(), inq[now]=0;

for(i=0; i<n; i++)

if(map[now][i]&&to[now]+map[now][i]<to[i]){

to[i]=to[now]+map[now][i];

if(!inq[i]) q.push(i), inq[i]=1;

} }

for(dis=from[t], ans=INF, i=0; i<n; i++){

if(from[i]!=INF) for(j=0; j<n; j++)

if(map[i][j]&&to[j]!=INF&&from[i]+to[j]+map[i][j ]!=dis&&from[i]+to[j]+map[i][j]<ans) ans=from[i]+to[j]+map[i][j];

}

if(ans==INF) puts("-1");

else printf("%d\n", ans);

}

return 0;

}

4 4. String Matching

4.1 AC Automaton

#include<iostream>

#include<queue>

using namespace std;

struct linked_list{

int num;

linked_list *next, *from;

linked_list(){

num=0;

next=from=NULL;

} };

struct ACA{

ACA *next[26], *fail;

linked_list head;

ACA(){

memset(next, 0, sizeof(ACA*)*26);

head.next=head.from=NULL;

head.num=0;

fail=NULL;

} } *root;

const int PAT_NUM=150, PAT_LEN=80, STR_LEN=1000010;

char pat[PAT_NUM][PAT_LEN], str[STR_LEN];

int cnt[PAT_NUM], max_cnt;

queue<ACA*> q;

void clear(ACA *now){

if(now==NULL) return;

for(int i=0; i<26; i++)

if(now->next[i]!=now) clear(now->next[i]);

linked_list *lptr=&(now->head);

while(lptr->next!=NULL&&lptr->next->from==lptr) lptr=lptr->next;

while(lptr->from!=NULL){

lptr=lptr->from;

delete lptr->next;

}

delete now;

return;

}

void insert(int i, int j, ACA *now){

if(!pat[i][j]){

linked_list *lptr=&(now->head);

while(lptr->next!=NULL) lptr=lptr->next;

lptr->next=new linked_list();

lptr->next->from=lptr;

lptr->next->num=i;

3

(4)

return;

}

if(now->next[pat[i][j]-’a’]==NULL) now->next[pat[i][j]-’a’]=new ACA();

insert(i, j+1, now->next[pat[i][j]-’a’]);

return;

}

void construct_ACA(){

int i;

ACA *curr, *next, *ptr;

linked_list *lptr;

while(!q.empty()) q.pop();

for(i=0; i<26; i++) if(root->next[i]!=root){

next=root->next[i];

next->fail=root;

q.push(next);

}

while(!q.empty()){

curr=q.front(); q.pop();

for(i=0; i<26; i++) if(curr->next[i]!=NULL){

next=curr->next[i];

q.push(next);

ptr=curr->fail;

while(ptr->next[i]==NULL) ptr=ptr->fail;

next->fail=ptr->next[i];

lptr=&(next->head);

while(lptr->next!=NULL) lptr=lptr->next;

lptr->next=(next->fail->head).next;

} } return;

}

void solve(){

ACA *st=root;

linked_list *lptr;

int i;

for(i=0; str[i]; i++){

while(st->next[str[i]-’a’]==NULL) st=st->fail;

st=st->next[str[i]-’a’];

for(lptr=&(st->head); lptr->next!=NULL; lptr=lptr->next) {

cnt[lptr->next->num]++;

max_cnt=max(cnt[lptr->next->num], max_cnt);

} } return;

}

int main(){

int n, i;

while(scanf("%d", &n), n){

clear(root);

root=new ACA();

max_cnt=0;

for(i=0; i<n; i++){

scanf("%s", pat[i]);

cnt[i]=0;

insert(i, 0, root);

}

scanf("%s", str);

for(i=0; i<26; i++)

if(root->next[i]==NULL) root->next[i]=root;

construct_ACA();

solve();

printf("%d\n", max_cnt);

for(i=0; i<n; i++) if(cnt[i]==max_cnt)

printf("%s\n", pat[i]);

}

return 0;

}

4.2 KMP

#include<iostream>

using namespace std;

char str[500001], cmp[10001];

int next[10001]={-1};

int main(){

int i, j, t, q;

scanf("%d ", &t);

while(t--){

gets(str);

scanf("%d ", &q);

while(q--){

gets(cmp);

for(i=0, j=-1; cmp[i]; next[++i]=++j) while(j>=0&&cmp[j]!=cmp[i]) j=next[j];

for(i=j=0; str[i]&&cmp[j]; i++, j++) while(j>=0&&cmp[j]!=str[i]) j=next[j];

puts(cmp[j]?"n":"y");

} }

return 0;

}

4.3 Sux Array

#include<iostream>

#define N 100001 using namespace std;

char s[N];

int rk[N], sa[N], t[N], d, f, len;

bool cmp(const int &a, const int &b){return rk[a]==rk[b]?rk[

a+d<?len]<rk[b+d<?len]:rk[a]<rk[b];}

int main(){

int i, j;

for(i=j=0, len=strlen(gets(s)); i<len; i++) rk[sa[i]=i]=s[

i];

for(f=1; (d=f>>1)<len&&j<=len; f<<=1){

sort(sa, sa+len, cmp);

for(i=0,j=1; i<len; i++)

t[sa[i]]=rk[sa[i]]==rk[sa[i+1]]&&rk[sa[i]+d<?len]==rk[

sa[i+1]+d<?len]?j:j++;

memcpy(rk, t, len*4);

}

for(i=0; i<len; i++) printf("%d\n", sa[i]);

return 0;

}

4.4 Trie

#include<iostream>

using namespace std;

struct trienode{

trienode* a[26];

char s[11];

trienode(){

memset(a, 0, sizeof(trienode*)*26);

memset(s, 0, sizeof(s));

}

}*root=new trienode(), *p;

void insert_word(char* m, char* s){

for(p=root; *s; s++){

if(!p->a[*s-’a’]) p->a[*s-’a’]=new trienode();

p=p->a[*s-’a’];

}

strcpy(p->s, m);

}

char* find_word(char* s){

for(p=root; *s; s++)

if(p->a[*s-’a’]) p=p->a[*s-’a’];

else return "eh";

if(p->s[0]) return p->s;

else return "eh";

}

int main(){

char word[11], mean[11], str[30];

while(gets(str), str[0]){

sscanf(str, " %s %s", mean, word);

insert_word(mean, word);

}

while(~scanf(" %s", word)) puts(find_word(word));

return 0;

}

5 5. STL

5.1 STL Heap

#include<iostream>

#include<algorithm>

using namespace std;

int main(){

int ans=0, p[30000], n, i;

scanf("%d", &n);

for(i=0; i<n; i++) scanf("%d", p+i);

make_heap(p, p+n, greater<int>());

while(n>1){

i=p[0];

pop_heap(p, p+n--, greater<int>());

i+=p[0];

pop_heap(p, p+n--, greater<int>());

ans+=i;

p[n]=i;

push_heap(p, p+(++n), greater<int>());

}

printf("%d\n", ans);

4

(5)

return 0;

}

5.2 using STL

#include<iostream>

#include<vector>

#include<set>

#include<map>

#include<queue>

using namespace std;

struct coor{int x, y;};

int main(){

vector<int> v;

vector<int>::iterator it;

v.push_back(10);

v.push_back(3);

for(it=v.begin(); it!=v.end(); it++){

printf("%d\n", *it);

} v[1]=321;

printf("v[1]=%d\n\n", v[1]);

v.clear();

v.push_back(100);

v=vector<int>();

//vector

set<int> s;

s.insert(10);

if(s.find(10)!=s.end()) puts("find!!");

else puts("QQ~");

s.erase(10);

if(s.find(10)!=s.end()) puts("find!!");

else puts("QQ~");

s.insert(50);

if(s.find(50)!=s.end()) puts("find!!");

else puts("QQ~");

s.erase(s.find(50));

if(s.find(50)!=s.end()) puts("find!!");

else puts("QQ~");

//set

map<int, int> m;

map<int, int>::iterator mit;

m[10]=3;

m[15]=100;

m[2]=111;

printf("%d\n", m[10]);

for(mit=m.begin(); mit!=m.end(); mit++)

printf("first & second are %d %d\n", (*mit).first, mit->

second);

//map<int, vector<int>> m2; error map<int, vector<int> > m2;

m2[1]=v;

map<string, int> ms;

ms["XD~"]=100;

printf("%d\n", ms["XD~"]);

//map

queue<coor> q;

coor tmp;

q.push( (coor){1, 3} );

while(!q.empty()){

tmp=q.front(); q.pop();

printf("coor is (%d %d)\n", tmp.x, tmp.y);

} //queue

system("pause");

return 0;

}

6 6. Other

6.1 Heap

#include<iostream>

#define Max(a,b) a>?b

#define Swap(a,b,t) t=a,a=b,b=t

#define N 10001 using namespace std;

int heap[N], n=1, tmp;

void heap_insert(int t){

int index=n++;

heap[index] = t;

while(index != 1){

if(heap[index>>1] < heap[index])

Swap(heap[index>>1], heap[index], tmp);

else return;

index >>= 1;

} }

int heap_pop(){

int t=heap[1], index=1, m;

heap[1] = heap[--n];

while(1){

if((index<<1)+1 < n && heap[(index<<1)+1] > heap[index

<<1]) m = (index<<1)+1;

else if(index<<1 < n) m = index<<1;

else m = index;

if(m > index && heap[index] < heap[m]) Swap(heap[index], heap[m], tmp);

else break;

index = m;

/*index <<= 1;

if(index >= n) break;

if(index+1 >= n){

if(heap[index>>1] < heap[index])

Swap(heap[index>>1], heap[index], tmp);

else break;

} else{

m = Max(heap[index], heap[index+1]);

if(heap[index>>1] < m)

Swap(heap[index>>1], m==heap[index]?heap[index]:heap [index+1], tmp);

else break;

if(m == heap[index+1]) index++;

}*/

}

return t;

}

void print_heap(){

for(int i = 1; i < n; i++) printf("%d ", heap[i]);

putchar(’\n’);

}

int main(){//max heap int d, n;

while(scanf("%d", &d), d){

if(d == 1){

scanf("%d", &n);

heap_insert(n);

printf("insert %d\n", n);

}

else if(d == 2){

printf("pop %d\n", heap_pop());

}

else if(d == 3) print_heap();

}

return 0;

}

6.2 Minimun Encloseing Circle

#include<iostream>

#include<cmath>

using namespace std;

struct coor{double x, y;} p[1000001], tmp;

struct circle{double r; coor c;} min_cir;

inline double sq(double a){return a*a;}

inline double dis(coor a, coor b){return sq(a.x-b.x)+sq(a.y- b.y);}

circle calc_3(coor a, coor b, coor c){

coor v1={b.x-a.x, b.y-a.y}, v2={c.x-a.x, c.y-a.y};

double c1=(sq(b.x)+sq(b.y)-sq(a.x)-sq(a.y))/2, c2=(sq(c.x) +sq(c.y)-sq(a.x)-sq(a.y))/2;

tmp.x=(v2.y*c1-v1.y*c2)/(v1.x*v2.y-v2.x*v1.y); tmp.y=(v2.x

*c1-v1.x*c2)/(v2.x*v1.y-v1.x*v2.y);

circle now={dis(a, tmp), tmp};

return now;

}

circle calc_2(int n, coor a, coor b){

tmp.x=(a.x+b.x)/2; tmp.y=(a.y+b.y)/2;

circle now={dis(a, tmp), tmp};

for(int i=0; i<n; i++) if(dis(p[i], now.c)>now.r)

now=calc_3(a, b, p[i]);

return now;

}

circle calc_1(int n, coor a){

tmp.x=(a.x+p[0].x)/2; tmp.y=(a.y+p[0].y)/2;

circle now={dis(a, tmp), tmp};

for(int i=1; i<n; i++) if(dis(p[i], now.c)>now.r)

now=calc_2(i, a, p[i]);

return now;

}

5

(6)

int main(){

int n, m, i;

while(scanf("%d%d", &m, &n), n|m){

for(i=0; i<n; i++) scanf("%lf%lf", &p[i].x, &p[i].y);

tmp.x=(p[0].x+p[1].x)/2; tmp.y=(p[0].y+p[1].y)/2;

min_cir=(circle){dis(p[0], tmp), tmp};

for(i=2; i<n; i++)

if(dis(p[i], min_cir.c)>min_cir.r) min_cir=calc_1(i, p[i]);

printf("%.3lf\n", sqrt(min_cir.r));

}

return 0;

}

6.3 Rectangle Cover Area

#include<iostream>

using namespace std;

const int L=1000000, N=100000;

struct NODE{int l, r, cnt, cov;} node[2100000];

struct LINE{int y, l, r; bool isd;} line[N*2];

bool operator <(const LINE &a, const LINE &b){return a.y<b.y

;};

void init(int i, int l, int r){

node[i].cnt=node[i].cov=0; node[i].l=l; node[i].r=r;

if(l+1==r) return;

init(i*2, l, (l+r)>>1); init(i*2+1, (l+r)>>1, r);

}

void calc(int i, LINE x){

if(node[i].r<=x.l||x.r<=node[i].l) return;

if(x.l<=node[i].l&&node[i].r<=x.r){

node[i].cnt+=x.isd?1:-1;

}else{

calc(i*2, x);

calc(i*2+1, x);

}

if(node[i].cnt) node[i].cov=node[i].r-node[i].l;

else node[i].cov=node[i].l+1==node[i].r?0:node[i*2].cov+

node[i*2+1].cov;

}

int main(){

int i, l, r, d, u, n, max=0, min=L;

long long ans=0;

scanf("%d", &n);

for(i=0, n<<=1; i<n; i+=2){

scanf("%d%d%d%d", &l, &r, &d, &u);

line[i]=(LINE){d, l, r, 1}; line[i+1]=(LINE){u, l, r, 0};

if(max<r) max=r; if(min>l) min=l;

}

init(1, min, max);

sort(line, line+n);

calc(1, line[0]);

for(i=1; i<n; i++){

ans+=(long long)node[1].cov*(line[i].y-line[i-1].y);

calc(1, line[i]);

}

printf("%I64d\n", ans);

return 0;

}

6

參考文獻

相關文件

[r]

[r]

[r]

[r]

[r]

• A sequence of numbers between 1 and d results in a walk on the graph if given the starting node.. – E.g., (1, 3, 2, 2, 1, 3) from

除了新聞報導,可以查看網路 評價(如 Google

oBike 標榜「騎到哪、停到哪」,大量放置可 租借的單車,但隨後各地開始出現棄置、違規