Hướng dẫn giải của Tam giác vuông
Chỉ dùng lời giải này khi không có ý tưởng, và đừng copy-paste code từ lời giải này. Hãy tôn trọng người ra đề và người viết lời giải.
Nộp một lời giải chính thức trước khi tự giải là một hành động có thể bị ban.
Nộp một lời giải chính thức trước khi tự giải là một hành động có thể bị ban.
Lưu ý: Các code mẫu dưới đây chỉ mang tính tham khảo và có thể không AC được bài tập này
Code mẫu của flashmt
const fi=''; fo=''; maxn=1505; delta:real=10000000000; type ar=array[1..maxn] of longint; arr=array[1..maxn] of real; var n,re,m,mm:longint; x,y,d,dd:ar; a,aa:arr; procedure rf; var i:longint; begin readln(n); for i:=1 to n do readln(x[i],y[i]); end; procedure rotatecalc(i:longint); var j,t,u,dem:longint; begin dem:=0; for j:=1 to n do begin if j=i then continue; dem:=dem+1; t:=x[j]-x[i]; u:=y[j]-y[i]; if t=0 then a[dem]:=delta else a[dem]:=u/t; if u=0 then aa[dem]:=delta else aa[dem]:=-t/u; end; end; procedure sort(var a:arr;l,r:longint); var i,j:longint; x,t:real; begin i:=l; j:=r; x:=a[(i+j) shr 1]; repeat while a[i]<x do i:=i+1; while a[j]>x do j:=j-1; if i<=j then begin t:=a[i]; a[i]:=a[j]; a[j]:=t; i:=i+1; j:=j-1; end; until i>j; if i<r then sort(a,i,r); if l<j then sort(a,l,j); end; procedure edit(var a:arr;var d:ar;var m:longint); var i:longint; begin m:=1; d[1]:=1; for i:=2 to n do if a[i]<>a[m] then begin m:=m+1; a[m]:=a[i]; d[m]:=1; end else d[m]:=d[m]+1; end; procedure pr; var i,j,k:longint; begin re:=0; for i:=1 to n do begin rotatecalc(i); sort(a,1,n-1); sort(aa,1,n-1); edit(a,d,m); edit(aa,dd,mm); j:=1; k:=1; while (j<=m) and (k<=mm) do begin if a[j]<aa[k] then j:=j+1 else begin if a[j]=aa[k] then re:=re+d[j]*dd[k]; k:=k+1; end; end; end; end; procedure wf; begin writeln(re shr 1); end; begin assign(input,fi); reset(input); assign(output,fo); rewrite(output); rf; pr; wf; close(input); close(output); end.
Code mẫu của ladpro98
#include <iostream> #include <cstdio> #include <algorithm> #define ii pair<int, int> #define X first #define Y second const int N = 1555; const long double eps = 1e8; using namespace std; ii v[N]; ii a[N]; int n, top; int gcd(int a, int b) { while (b) a %= b, swap(a, b); return a; } void refine(ii &v) { int g = gcd(v.X, v.Y); v.X /= g; v.Y /= g; if (v.X < 0) { v.X = -v.X; v.Y = -v.Y; } } int main() { ios :: sync_with_stdio(0); cin >> n; for(int i = 1; i <= n; i++) cin >> a[i].X >> a[i].Y; int res = 0; ii t; for(int i = 1; i <= n; i++) { top = 0; for(int j = 1; j <= n; j++) if (i != j) v[top++] = ii(a[i].X - a[j].X, a[i].Y - a[j].Y); for(int j = 0; j < top; j++) refine(v[j]); sort(v, v + top); for(int j = 0; j < top; j++) { t = ii(v[j].Y, -v[j].X); if (t.X < 0) {t.X = -t.X; t.Y = -t.Y;} res += upper_bound(v + j + 1, v + top, t) - lower_bound(v + j + 1, v + top, t); } } cout << res; return 0; }
Code mẫu của RR
//Written by Nguyen Thanh Trung //Finally I am able to solve this problem {$R+,Q+,N+} {$Mode objFPC} uses math; const FINP=''; FOUT=''; MAXN=1511; eps=1e-14; type point=record x,y:double; end; var f1,f2:text; n:longint; a:array[1..MAXN] of point; goc:array[1..MAXN] of double; count:array[1..MAXN] of longint; procedure openF; begin assign(f1,FINP); reset(f1); assign(f2,FOUT); rewrite(f2); end; procedure closeF; begin close(f1); close(f2); end; procedure inp; inline; var i:longint; begin read(f1,n); for i:=1 to n do with a[i] do read(f1,x,y); end; procedure swapd(var a,b:double); inline; var temp:double; begin temp:=a; a:=b; b:=temp; end; var mid:double; procedure sort(l,r:longint); inline; var i,j:longint; begin i:=l; j:=r; mid:=goc[l+random(r-l+1)]; repeat while goc[i]<mid do inc(i); while goc[j]>mid do dec(j); if i<=j then begin swapd(goc[i],goc[j]); inc(i); dec(j); end; until i>j; if i<r then sort(i,r); if l<j then sort(l,j); end; procedure solve; var i,ii,k,now,prev:longint; countx,county,sl,kq:longint; begin kq:=0; for i:=1 to n do begin countx:=0; county:=0; sl:=0; for ii:=1 to n do if ii<>i then if a[i].x=a[ii].x then inc(countx) else if a[i].y=a[ii].y then inc(county) else begin inc(sl); goc[sl]:=arctan((a[ii].y-a[i].y)/(a[ii].x-a[i].x)); end; kq+=countx*county; if sl<2 then continue; sort(1,sl); k:=1; count[1]:=1; for ii:=2 to sl do if goc[ii]>goc[k]+eps then begin inc(k); goc[k]:=goc[ii]; count[k]:=1; end else count[k]+=1; sl:=k; prev:=0; for now:=1 to sl do begin while (prev<sl) and (goc[prev+1]<goc[now]-pi/2+eps) do inc(prev); if (prev>0) and (abs(goc[now]-goc[prev]-pi/2)<eps) then kq+=count[now]*count[prev]; end; end; writeln(f2,kq); end; begin openF; inp; solve; closeF; end.
Code mẫu của hieult
#include<cstdio> #include<cmath> #include<cstring> #include<cstdlib> #include<cassert> #include<ctime> #include<algorithm> #include<iterator> #include<iostream> #include<cctype> #include<string> #include<vector> #include<map> #include<set> #include<queue> #include<list> //#include<conio.h> #define maxn 1502 #define oo 1111111111 #define base 100000000 #define TR(c, it) for(typeof((c).begin()) it=(c).begin(); it!=(c).end(); it++) long double const PI= acos((long double)(-1)); long double const ep = 0.000000000001; using namespace std; typedef pair<int, int> II; typedef vector<int> VI; typedef vector<II> VII; typedef vector<VI> VVI; typedef vector<VII> VVII; typedef long double ld; void OPEN(){ freopen("A.in", "r", stdin); freopen("A.out", "w", stdout); } struct diem{ long long x,y; }; struct vec_tor{ long long x,y; long double goc; vec_tor(){}; vec_tor(diem D1,diem D2){ x = D2.x-D1.x; y = D2.y-D1.y; if(y<0){ x = -x; y = -y; } if(y==0) x>0?x:-x; goc = atan2((ld)y,(ld)x); } bool operator <(vec_tor T)const{ return (x*T.y>y*T.x);// && x * T.x >= 0 && y * T.y >= 0); } bool operator ==(vec_tor T)const{ return ( x*T.y == y*T.x && x * T.x >= 0 && y * T.y >= 0); } int vuonggoc(vec_tor T) const{ if (x*T.x==-y*T.y) return 0; if(x * T.x + y * T.y > 0) return 1; return -1; } }; diem A[1511]; vec_tor V[3011]; long long KQ = 0; int n; int main(){ //OPEN(); scanf("%d",&n); for(int i = 0;i<n;i++) scanf("%lld %lld",&A[i].x,&A[i].y); for(int i = 0;i<n;i++){ int t = 0; for(int j = 0;j<n;j++){ if(i!=j) V[t++] = vec_tor(A[i],A[j]); } sort(V,V+t); int u=0,run = 0; for(int j = 0;j<t;j++){ if(j>0 && V[j]==V[j-1]){ KQ+=run; continue; } while(V[j].vuonggoc(V[u]) == 1 && u<t) u++; run = 0; while(V[j].vuonggoc(V[u]) == 0 && u<t){ u++; run++; KQ++; } } } printf("%lld",KQ); //getch(); }
Code mẫu của ll931110
{$inline on} {$N+} program PRAVO; const input = ''; output = ''; maxn = 1500; eps = 1e-13; var a,b,t: array[1..maxn] of longint; q,s: array[1..maxn] of extended; nb,cc: longint; n: longint; time: longint; res: longint; procedure init;inline; var f: text; i: longint; begin assign(f, input); reset(f); readln(f, n); for i := 1 to n do readln(f, a[i], b[i]); close(f); end; procedure sort(l,h: longint);inline; var i,j: longint; p,tmp: extended; begin if l >= h then exit; i := l; j := h; p := s[random(h - l + 1) + l]; repeat while s[i] < p do inc(i); while s[j] > p do dec(j); if i <= j then begin if i < j then begin tmp := s[i]; s[i] := s[j]; s[j] := tmp; end; inc(i); dec(j); end; until i > j; sort(l,j); sort(i,h); end; procedure press;inline; var i: longint; begin nb := 0; if cc = 0 then exit; inc(nb); q[1] := s[1]; t[1] := 1; for i := 2 to cc do if s[i] > s[i - 1] then begin inc(nb); q[nb] := s[i]; t[nb] := 1; end else inc(t[nb]); end; function equ(x,y: extended): boolean;inline; begin equ := abs(x - y) < eps; end; function find(i: longint): longint;inline; var inf,sup,med: longint; x: extended; begin inf := i + 1; sup := nb; x := -1/q[i]; repeat med := (inf + sup) div 2; if equ(q[med],x) then exit(t[med]) else if q[med] > x then sup := med - 1 else inf := med + 1; until inf > sup; find := 0; end; procedure calc(x: longint);inline; var i,n0,ninf: longint; begin cc := 0; n0 := 0; ninf := 0; for i := 1 to n do if i <> x then if b[i] = b[x] then inc(ninf) else if a[i] = a[x] then inc(n0) else begin inc(cc); s[cc] := (b[i] - b[x]) / (a[i] - a[x]); end; if cc = 0 then exit; sort(1,cc); press; for i := 1 to nb - 1 do res := res + t[i] * find(i); res := res + n0 * ninf; end; procedure solve;inline; var i: longint; begin res := 0; for i := 1 to n do calc(i); end; procedure printresult;inline; var f: text; begin assign(f, output); rewrite(f); writeln(f, res); close(f); end; begin init; solve; printresult; end.
Code mẫu của khuc_tuan
const Epsilon = 1E-12; Max = 1500; var goc, x, y: array[1..Max] of extended; Left, Right:array[1..Max] of extended; key, result: extended; m, n, c: longint; procedure Read_Data; var i: longint; begin Read(n); For i := 1 to n do Read(x[i], y[i]); end; procedure Swap(i, j: longint); var temp: extended; begin temp := goc[i]; goc[i] := goc[j]; goc[j] := temp; end; procedure Sort(L, R: longint); var i, j: longint; k: extended; begin If L >= R then Exit; i := L; j := R; k := goc[(i+j) shr 1]; Repeat While goc[i] < k do inc(i); While goc[j] > k do dec(j); if i <= j then begin If i < j then Swap(i, j); inc(i); dec(j); end; Until i > j; Sort(L, j); Sort(i, R); end; function theta(x1, y1, x2, y2: extended): extended; var t, dx, dy, ax, ay: extended; begin dx := x2 - x1; ax := abs(dx); dy := y2 - y1; ay := abs(dy); If (dx = 0) and (dy = 0) then t := 0 else t := dy/(ax + ay); If dx < 0 then t := 2 - t else if dy < 0 then t := 4 + t; theta := t * 90; end; procedure Calculate; var i: longint; begin For i := 2 to m do If abs(Goc[i] - Goc[i-1]) < Epsilon then Left[i] := Left[i-1]; For i := m-1 downto 1 do If abs(Goc[i] - Goc[i+1]) < Epsilon then Right[i] := Right[i+1]; end; procedure Init(i: longint); var j: longint; begin m := 0; For j := 1 to n do If j <> i then begin m := m + 1; Left[m] := m; Right[m] := m; Goc[m] := theta(x[i], y[i], x[j], y[j]); end; Sort(1, m); Calculate; end; procedure Find_Key(i: longint); begin If abs(Goc[i] - 270) < Epsilon then begin key := 0; Exit; end; If Goc[i] < 270 then key := Goc[i] + 90 Else key := Goc[i] - 270; end; procedure Binary_search; var L, R, mid: longint; begin c := 0; L := 1; R := m; Repeat mid := (L + R) shr 1; If abs(Goc[mid] - key) < Epsilon then begin c := mid; Break; end else If Goc[mid] < key then L := mid + 1 else R := mid - 1; Until L > R; end; procedure Solve; var i, j: longint; begin result := 0; For i := 1 to n do begin Init(i); For j := 1 to m do begin Find_key(j); Binary_search; If c > 0 then result := result + Right[c] - Left[c] + 1; end; end; end; procedure Write_answer; begin Writeln( result :0: 0); end; begin Read_Data; Solve; Write_answer; end.
Bình luận