Submission #15440866
Source Code Expand
Copy
#[allow(unused_macros, dead_code)]
macro_rules! input {
(source = $s:expr, $($r:tt)*) => {
let mut iter = $s.split_whitespace();
let mut next = || { iter.next().unwrap() };
input_inner!{next, $($r)*}
};
($($r:tt)*) => {
let stdin = std::io::stdin();
let mut bytes = std::io::Read::bytes(std::io::BufReader::new(stdin.lock()));
let mut next = move || -> String{
bytes
.by_ref()
.map(|r|r.unwrap() as char)
.skip_while(|c|c.is_whitespace())
.take_while(|c|!c.is_whitespace())
.collect()
};
input_inner!{next, $($r)*}
};
}
#[allow(unused_macros, dead_code)]
macro_rules! input_inner {
($next:expr) => {};
($next:expr, ) => {};
($next:expr, $var:ident : $t:tt $($r:tt)*) => {
let $var = read_value!($next, $t);
input_inner!{$next $($r)*}
};
($next:expr, mut $var:ident : $t:tt $($r:tt)*) => {
let mut $var = read_value!($next, $t);
input_inner!{$next $($r)*}
};
}
#[allow(unused_macros, dead_code)]
macro_rules! read_value {
($next:expr, ( $($t:tt),* )) => {
( $(read_value!($next, $t)),* )
};
($next:expr, [ $t:tt ; $len:expr ]) => {
(0..$len).map(|_| read_value!($next, $t)).collect::<Vec<_>>()
};
($next:expr, chars) => {
read_value!($next, String).chars().collect::<Vec<char>>()
};
($next:expr, bytes) => {
read_value!($next, String).into_bytes()
};
($next:expr, usize1) => {
read_value!($next, usize) - 1
};
($next:expr, $t:ty) => {
$next().parse::<$t>().expect("Parse error")
};
}
#[allow(dead_code)]
struct UnionFind {
parent: Vec<usize>,
rank: Vec<usize>,
size: Vec<usize>,
}
#[allow(dead_code)]
impl UnionFind {
fn new(n: usize) -> UnionFind {
let mut p = vec![0; n];
for i in 0..n {
p[i] = i;
}
return UnionFind {
parent: p,
rank: vec![0; n],
size: vec![1; n],
};
}
fn find(&mut self, x: usize) -> usize {
if x == self.parent[x] {
x
} else {
let p = self.parent[x];
let pr = self.find(p);
self.parent[x] = pr;
pr
}
}
fn same(&mut self, a: usize, b: usize) -> bool {
self.find(a) == self.find(b)
}
fn unite(&mut self, a: usize, b: usize) {
let a_root = self.find(a);
let b_root = self.find(b);
if a_root == b_root {
return;
}
if self.rank[a_root] > self.rank[b_root] {
self.parent[b_root] = a_root;
self.size[a_root] += self.size[b_root];
} else {
self.parent[a_root] = b_root;
self.size[b_root] += self.size[a_root];
if self.rank[a_root] == self.rank[b_root] {
self.rank[b_root] += 1;
}
}
}
fn get_size(&mut self, x: usize) -> usize {
let root = self.find(x);
self.size[root]
}
}
const MOD_P: usize = 1000000007;
#[allow(dead_code)]
// fact(n) = n! mod p
fn fact(n: usize) -> usize {
let mut acc = 1;
for i in 1..n + 1 {
acc = acc * i % MOD_P;
}
acc
}
#[allow(dead_code)]
fn mod_pow(b: usize, mut e: usize) -> usize {
let mut base = b;
let mut acc = 1;
while e > 1 {
if e % 2 == 1 {
acc = acc * base % MOD_P;
}
e /= 2;
base = base * base % MOD_P;
}
if e == 1 {
acc = acc * base % MOD_P;
}
acc
}
#[allow(dead_code)]
fn comb(n: usize, r: usize) -> usize {
// nCr = n! / (r! (n-r)!) = n! (r!)^(p-2) ((n-r)!)^(p-2)
let x = ((n - r + 1)..(n + 1)).fold(1, |p, x| p * x % MOD_P);
let y = mod_pow(fact(r), MOD_P - 2);
x * y % MOD_P
}
#[derive(Clone, Copy, Debug)]
struct GF(usize);
impl std::ops::Add for GF {
type Output = GF;
fn add(self, rhs: GF) -> Self::Output {
let mut d = self.0 + rhs.0;
if d >= MOD_P {
d -= MOD_P;
}
GF(d)
}
}
impl std::ops::AddAssign for GF {
fn add_assign(&mut self, rhs: GF) {
*self = *self + rhs;
}
}
impl std::ops::Sub for GF {
type Output = GF;
fn sub(self, rhs: GF) -> Self::Output {
let mut d = self.0 + MOD_P - rhs.0;
if d >= MOD_P {
d -= MOD_P;
}
GF(d)
}
}
impl std::ops::SubAssign for GF {
fn sub_assign(&mut self, rhs: GF) {
*self = *self - rhs;
}
}
impl std::ops::Mul for GF {
type Output = GF;
fn mul(self, rhs: GF) -> Self::Output {
let mut d = self.0 * rhs.0;
d %= MOD_P;
GF(d)
}
}
impl std::ops::MulAssign for GF {
fn mul_assign(&mut self, rhs: GF) {
*self = *self * rhs;
}
}
impl std::fmt::Display for GF {
fn fmt<'a>(&self, f: &mut std::fmt::Formatter<'a>) -> std::fmt::Result {
write!(f, "{}", self.0)
}
}
#[allow(dead_code)]
impl GF {
pub fn new(n: usize) -> GF {
GF(n % MOD_P)
}
pub fn zero() -> GF {
GF(0)
}
pub fn one() -> GF {
GF(1)
}
pub fn pow(self, mut e: usize) -> GF {
let mut acc = GF::one();
let mut b = self;
while e > 1 {
if e % 2 == 1 {
acc *= b;
}
b *= b;
e /= 2;
}
if e == 1 {
acc *= b;
}
acc
}
pub fn fact(self) -> GF {
let mut acc = GF::one();
for i in 1..=self.0 {
acc *= GF::new(i);
}
acc
}
pub fn inv(self) -> GF {
self.pow(MOD_P - 2)
}
pub fn comb(n: GF, r: GF) -> GF {
// nCr = n! / (r! (n-r)!) = n! (r!)^(p-2) ((n-r)!)^(p-2)
let x = ((n.0 - r.0 + 1)..=n.0).fold(GF::one(), |p, x| p * GF(x));
let y = r.fact().inv();
x * y
}
}
#[allow(dead_code)]
#[derive(Debug)]
struct MemComb {
inv: Vec<GF>,
fact: Vec<GF>,
factinv: Vec<GF>,
}
#[allow(dead_code)]
impl MemComb {
pub fn new(n: usize) -> MemComb {
let mut inv = vec![GF::one(); n + 1];
let mut fact = vec![GF::one(); n + 1];
let mut factinv = vec![GF::one(); n + 1];
for i in 2..=n {
fact[i] = fact[i - 1] * GF(i);
}
factinv[n] = fact[n].inv();
for i in (1..n).rev() {
factinv[i] = factinv[i + 1] * GF(i + 1); // 1/n! = 1/(n+1)! * (n+1)
inv[i] = factinv[i] * fact[i - 1]; // 1/n = 1/n! * (n-1)!
}
inv[n] = factinv[n] * fact[n - 1];
MemComb { inv, fact, factinv }
}
pub fn comb(&self, n: usize, r: usize) -> GF {
if n >= r {
self.fact[n] * self.factinv[r] * self.factinv[n - r]
} else {
GF::zero()
}
}
}
#[allow(dead_code)]
fn gcd(a: usize, b: usize) -> usize {
if b > a {
gcd(b, a)
} else if a % b == 0 {
b
} else {
gcd(b, a % b)
}
}
#[allow(dead_code)]
fn getline() -> String {
let mut __ret = String::new();
std::io::stdin().read_line(&mut __ret).ok();
return __ret;
}
#[allow(unused_imports)]
use std::cmp::{max, min};
fn main() {
input! {
n: usize,
xyp: [(isize, isize, isize); n]
}
let mut ansv = vec![std::isize::MAX; n + 1];
for k in 0..=n {
for kxbit in 0..(1 << k) {
for kybit in 0..(1 << k) {
let bits = ((kxbit as u64).count_ones() + (kybit as u64).count_ones()) as usize;
if bits > n {
break;
}
let mut acc = 0;
for (_i, &(x, y, p)) in xyp.iter().enumerate() {
let mut dist = min(x.abs(), y.abs());
for j in 0..k {
if kxbit & (1 << j) != 0 {
let lx = xyp[j].0;
dist = min((x - lx).abs(), dist);
}
}
for j in 0..k {
if kybit & (1 << j) != 0 {
let ly = xyp[j].1;
dist = min((y - ly).abs(), dist);
}
}
acc += dist * p;
}
ansv[bits] = min(ansv[bits], acc);
// ans = min(acc, ans);
}
}
}
for i in 0..=n {
println!("{}", ansv[i]);
}
}
Submission Info
Submission Time |
|
Task |
E - M's Solution |
User |
sly |
Language |
Rust (1.42.0) |
Score |
0 |
Code Size |
8569 Byte |
Status |
TLE |
Exec Time |
3308 ms |
Memory |
2160 KB |
Judge Result
Set Name |
Sample |
All |
Score / Max Score |
0 / 0 |
0 / 500 |
Status |
AC
|
|
Set Name |
Test Cases |
Sample |
|
All |
00-sample-01.txt, 00-sample-02.txt, 00-sample-03.txt, 01-corner-01.txt, 01-corner-02.txt, 01-corner-03.txt, 01-corner-04.txt, 01-corner-05.txt, 02-random-01.txt, 02-random-02.txt, 02-random-03.txt, 02-random-04.txt, 03-random-quarter-01.txt, 03-random-quarter-02.txt, 03-random-quarter-03.txt, 03-random-quarter-04.txt |
Case Name |
Status |
Exec Time |
Memory |
00-sample-01.txt |
AC |
9 ms |
1972 KB |
00-sample-02.txt |
AC |
3 ms |
2044 KB |
00-sample-03.txt |
AC |
22 ms |
2044 KB |
01-corner-01.txt |
TLE |
3308 ms |
1996 KB |
01-corner-02.txt |
TLE |
3308 ms |
2068 KB |
01-corner-03.txt |
TLE |
3308 ms |
2160 KB |
01-corner-04.txt |
AC |
6 ms |
2092 KB |
01-corner-05.txt |
AC |
2 ms |
2036 KB |
02-random-01.txt |
TLE |
3308 ms |
2052 KB |
02-random-02.txt |
TLE |
3308 ms |
1992 KB |
02-random-03.txt |
TLE |
3308 ms |
2048 KB |
02-random-04.txt |
TLE |
3308 ms |
2060 KB |
03-random-quarter-01.txt |
TLE |
3308 ms |
2080 KB |
03-random-quarter-02.txt |
TLE |
3308 ms |
2032 KB |
03-random-quarter-03.txt |
TLE |
3308 ms |
2028 KB |
03-random-quarter-04.txt |
TLE |
3308 ms |
1996 KB |