結果

問題 No.1053 ゲーミング棒
ユーザー へのくへのく
提出日時 2020-06-19 16:09:45
言語 Rust
(1.77.0 + proconio)
結果
WA  
実行時間 -
コード長 25,095 bytes
コンパイル時間 13,955 ms
コンパイル使用メモリ 406,468 KB
実行使用メモリ 9,744 KB
最終ジャッジ日時 2024-07-03 13:27:55
合計ジャッジ時間 14,407 ms
ジャッジサーバーID
(参考情報)
judge4 / judge5
このコードへのチャレンジ
(要ログイン)

テストケース

テストケース表示
入力 結果 実行時間
実行使用メモリ
testcase_00 AC 1 ms
6,812 KB
testcase_01 AC 1 ms
6,944 KB
testcase_02 AC 1 ms
6,940 KB
testcase_03 AC 0 ms
6,944 KB
testcase_04 AC 1 ms
6,940 KB
testcase_05 AC 1 ms
6,944 KB
testcase_06 AC 1 ms
6,940 KB
testcase_07 AC 1 ms
6,940 KB
testcase_08 AC 1 ms
6,944 KB
testcase_09 AC 1 ms
6,940 KB
testcase_10 AC 1 ms
6,940 KB
testcase_11 AC 1 ms
6,940 KB
testcase_12 AC 1 ms
6,940 KB
testcase_13 AC 1 ms
6,940 KB
testcase_14 AC 1 ms
6,944 KB
testcase_15 AC 1 ms
6,944 KB
testcase_16 AC 1 ms
6,940 KB
testcase_17 AC 1 ms
6,940 KB
testcase_18 AC 1 ms
6,940 KB
testcase_19 AC 1 ms
6,940 KB
testcase_20 AC 1 ms
6,944 KB
testcase_21 AC 1 ms
6,940 KB
testcase_22 AC 1 ms
6,940 KB
testcase_23 AC 15 ms
7,184 KB
testcase_24 AC 15 ms
7,184 KB
testcase_25 AC 21 ms
9,744 KB
testcase_26 AC 13 ms
7,188 KB
testcase_27 AC 1 ms
6,940 KB
testcase_28 AC 1 ms
6,944 KB
testcase_29 AC 1 ms
6,944 KB
testcase_30 AC 4 ms
6,940 KB
testcase_31 AC 3 ms
6,944 KB
testcase_32 AC 4 ms
6,940 KB
testcase_33 WA -
testcase_34 WA -
testcase_35 AC 5 ms
6,944 KB
testcase_36 AC 5 ms
6,944 KB
権限があれば一括ダウンロードができます

ソースコード

diff #

#![allow(unused_imports, non_snake_case)]
#![allow(dead_code)]
use crate::scanner::Scanner;
use crate::{data_structure::counter::Counter, misc::run_length_encoding};
fn main() {
    let mut scan = Scanner::new();
    let _n = scan.read::<i32>();
    let a = scan
        .read_line()
        .split_ascii_whitespace()
        .map(|s| s.parse::<i32>().unwrap())
        .collect();
    let r = run_length_encoding(&a).map(|t| t.1);
    let cnt = r.to::<Counter<_>>();
    if r.ilen() == 1 {
        println!("0");
        return;
    }
    if r[0] == *r.last_exn()
        && r.part(1..r.ilen() - 1)
            .into_iter()
            .collect::<Counter<_>>()
            .values()
            .all(|x| *x == 1)
    {
        println!("1");
        return;
    }
    if cnt.values().all(|x| *x == 1) {
        println!("0");
        return;
    }
    println!("-1");
}
pub mod arraylist {
    use crate::{ext::range::IntRangeBounds, independent::integer::Int};
    use std::fmt::Formatter;
    use std::iter::FromIterator;
    use std::ops::{Index, IndexMut, RangeBounds};
    use std::slice::Iter;
    #[derive(Clone, PartialEq, Eq)]
    pub struct List<T> {
        pub vec: Vec<T>,
    }
    impl<T> List<T> {
        #[inline]
        pub fn new() -> List<T> {
            List { vec: vec![] }
        }
        #[inline]
        pub fn init(init: T, n: i32) -> List<T>
        where
            T: Clone,
        {
            List {
                vec: vec![init; n as usize],
            }
        }
        #[inline]
        pub fn from_vec(vec: Vec<T>) -> List<T> {
            List { vec }
        }
        #[inline]
        pub fn ilen(&self) -> i32 {
            self.vec.len() as i32
        }
        #[inline]
        pub fn iter(&self) -> Iter<'_, T> {
            self.vec.iter()
        }
        #[inline]
        pub fn push(&mut self, item: T) {
            self.vec.push(item);
        }
        #[inline]
        pub fn sort(&mut self)
        where
            T: Ord,
        {
            self.vec.sort();
        }
        #[inline]
        pub fn reverse(&mut self) {
            self.vec.reverse();
        }
        #[inline]
        pub fn sort_by<F>(&mut self, compare: F)
        where
            F: FnMut(&T, &T) -> std::cmp::Ordering,
        {
            self.vec.sort_by(compare)
        }
        #[inline]
        pub fn sort_by_key<K, F>(&mut self, compare: F)
        where
            F: FnMut(&T) -> K,
            K: Ord,
        {
            self.vec.sort_by_key(compare)
        }
        #[inline]
        pub fn first(&self) -> Option<&T> {
            self.vec.first()
        }
        #[inline]
        pub fn last(&self) -> Option<&T> {
            self.vec.last()
        }
        #[inline]
        pub fn pop(&mut self) -> Option<T> {
            self.vec.pop()
        }
        #[inline]
        pub fn swap(&mut self, i: i32, j: i32) {
            self.vec.swap(i as usize, j as usize);
        }
        #[inline]
        pub fn append(&mut self, mut other: Self) {
            self.vec.append(&mut other.vec);
        }
        #[inline]
        pub fn extend(&mut self, other: impl Iterator<Item = T>) {
            self.vec.extend(other);
        }
        #[inline]
        pub fn mirror(&self) -> std::iter::Cloned<Iter<T>>
        where
            T: Clone,
        {
            self.iter().cloned()
        }
        #[inline]
        pub fn map<B, F>(&self, f: F) -> List<B>
        where
            T: Clone,
            F: FnMut(T) -> B,
        {
            self.mirror().map(f).collect()
        }
        #[inline]
        pub fn filter<P>(&self, predicate: P) -> List<T>
        where
            T: Clone,
            P: FnMut(&T) -> bool,
        {
            self.mirror().filter(predicate).collect()
        }
        #[inline]
        pub fn filter_map<B, F>(&self, f: F) -> List<B>
        where
            T: Clone,
            F: FnMut(T) -> Option<B>,
        {
            self.mirror().filter_map(f).collect()
        }
        #[inline]
        pub fn any<P>(&self, predicate: P) -> bool
        where
            P: FnMut(&T) -> bool,
        {
            self.iter().any(predicate)
        }
        #[inline]
        pub fn all<P>(&self, predicate: P) -> bool
        where
            P: FnMut(&T) -> bool,
        {
            self.iter().all(predicate)
        }
        #[inline]
        pub fn sum(&self) -> T
        where
            T: Int,
        {
            self.iter().cloned().fold(T::zero(), |acc, x| acc + x)
        }
        #[inline]
        pub fn enumerate(&self) -> List<(i32, T)>
        where
            T: Clone,
        {
            self.mirror()
                .enumerate()
                .map(|p| (p.0 as i32, p.1))
                .collect()
        }
        #[inline]
        pub fn find<P>(&self, mut predicate: P) -> Option<&T>
        where
            P: FnMut(&T) -> bool,
        {
            self.iter().find(|x| predicate(*x))
        }
        #[inline]
        pub fn index_of<P>(&self, mut predicate: P) -> Option<i32>
        where
            P: FnMut(&T) -> bool,
        {
            self.iter()
                .enumerate()
                .find(|&(_i, x)| predicate(x))
                .map(|p| p.0 as i32)
        }
        #[inline]
        pub fn to<B: FromIterator<T>>(&self) -> B
        where
            T: Clone,
        {
            self.mirror().collect()
        }
        #[inline]
        pub fn min(&self) -> Option<&T>
        where
            T: Ord,
        {
            self.iter().min()
        }
        #[inline]
        pub fn max(&self) -> Option<&T>
        where
            T: Ord,
        {
            self.iter().max()
        }
        #[inline]
        pub fn argmin(&self) -> Option<i32>
        where
            T: Ord,
        {
            let item = self.iter().min()?;
            self.iter()
                .enumerate()
                .find(|p| p.1 == item)
                .map(|p| p.0 as i32)
        }
        #[inline]
        pub fn argmax(&self) -> Option<i32>
        where
            T: Ord,
        {
            let item = self.iter().max()?;
            self.iter()
                .enumerate()
                .find(|p| p.1 == item)
                .map(|p| p.0 as i32)
        }
        #[inline]
        pub fn part<U>(&self, range: U) -> List<T>
        where
            T: Clone,
            U: RangeBounds<i32>,
        {
            List::from_vec(
                self.vec[range.lower_bound(0) as usize..range.upper_bound(self.ilen()) as usize]
                    .to_vec(),
            )
        }
        #[inline]
        pub fn first_exn(&self) -> &T {
            self.first().unwrap()
        }
        #[inline]
        pub fn last_exn(&self) -> &T {
            self.last().unwrap()
        }
        #[inline]
        pub fn pop_exn(&mut self) -> T {
            self.pop().unwrap()
        }
        #[inline]
        pub fn min_exn(&self) -> &T
        where
            T: Ord,
        {
            self.min().unwrap()
        }
        #[inline]
        pub fn max_exn(&self) -> &T
        where
            T: Ord,
        {
            self.max().unwrap()
        }
        #[inline]
        pub fn argmin_exn(&self) -> i32
        where
            T: Ord,
        {
            self.argmin().unwrap()
        }
        #[inline]
        pub fn argmax_exn(&self) -> i32
        where
            T: Ord,
        {
            self.argmax().unwrap()
        }
        #[inline]
        pub fn find_exn<P>(&self, predicate: P) -> &T
        where
            P: FnMut(&T) -> bool,
        {
            self.find(predicate).unwrap()
        }
        #[inline]
        pub fn index_of_exn<P>(&self, predicate: P) -> i32
        where
            P: FnMut(&T) -> bool,
        {
            self.index_of(predicate).unwrap()
        }
    }
    impl<T> Index<i32> for List<T> {
        type Output = T;
        #[inline]
        fn index(&self, index: i32) -> &Self::Output {
            if cfg!(debug_assertions) {
                self.vec.index(index as usize)
            } else {
                unsafe { self.vec.get_unchecked(index as usize) }
            }
        }
    }
    impl<T> IndexMut<i32> for List<T> {
        #[inline]
        fn index_mut(&mut self, index: i32) -> &mut Self::Output {
            if cfg!(debug_assertions) {
                self.vec.index_mut(index as usize)
            } else {
                unsafe { self.vec.get_unchecked_mut(index as usize) }
            }
        }
    }
    impl<T> FromIterator<T> for List<T> {
        fn from_iter<U: IntoIterator<Item = T>>(iter: U) -> Self {
            let mut vec = vec![];
            for i in iter {
                vec.push(i);
            }
            List { vec }
        }
    }
    impl<T> IntoIterator for List<T> {
        type Item = T;
        type IntoIter = std::vec::IntoIter<T>;
        fn into_iter(self) -> std::vec::IntoIter<T> {
            self.vec.into_iter()
        }
    }
    impl<'a, T> IntoIterator for &'a List<T> {
        type Item = &'a T;
        type IntoIter = Iter<'a, T>;
        fn into_iter(self) -> Iter<'a, T> {
            self.vec.iter()
        }
    }
    impl<T: std::fmt::Display> std::fmt::Display for List<T> {
        fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
            write!(
                f,
                "{}",
                self.iter()
                    .map(|x| format!("{}", x))
                    .collect::<Vec<_>>()
                    .join(" ")
            )
        }
    }
    impl<T: std::fmt::Debug> std::fmt::Debug for List<T> {
        fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
            write!(
                f,
                "[{}]",
                self.iter()
                    .map(|x| format!("{:?}", x))
                    .collect::<Vec<_>>()
                    .join(", ")
            )
        }
    }
    impl<T> From<Vec<T>> for List<T> {
        fn from(vec: Vec<T>) -> Self {
            Self::from_vec(vec)
        }
    }
    impl<T: Clone> From<&[T]> for List<T> {
        fn from(slice: &[T]) -> Self {
            slice.iter().cloned().collect()
        }
    }
    #[macro_export]
    macro_rules ! list { ( ) => { $ crate :: arraylist :: List :: new ( ) } ; ( $ init : expr ; $ ( $ dim : expr ) ;* ) => { list ! ( $ ( $ dim ) ;* => $ init ) } ; ( $ head : expr ; $ ( $ tail : expr ) ;* => $ init : expr ) => { $ crate :: arraylist :: List :: init ( list ! ( $ ( $ tail ) ;* => $ init ) , $ head ) } ; ( $ head : expr => $ init : expr ) => { $ crate :: arraylist :: List :: init ( $ init , $ head ) } ; }
}
pub mod independent {
    pub mod integer {
        pub trait Int:
            std::ops::Add<Output = Self>
            + std::ops::Sub<Output = Self>
            + std::ops::Mul<Output = Self>
            + std::ops::Div<Output = Self>
            + std::ops::Rem<Output = Self>
            + std::hash::Hash
            + PartialEq
            + Eq
            + PartialOrd
            + Ord
            + Copy
        {
            fn to_u8(&self) -> u8;
            fn to_u16(&self) -> u16;
            fn to_u32(&self) -> u32;
            fn to_u64(&self) -> u64;
            fn to_u128(&self) -> u128;
            fn to_i8(&self) -> i8;
            fn to_i16(&self) -> i16;
            fn to_i32(&self) -> i32;
            fn to_i64(&self) -> i64;
            fn to_i128(&self) -> i128;
            fn to_usize(&self) -> usize;
            fn to_isize(&self) -> isize;
            fn zero() -> Self;
            fn one() -> Self;
        }
        macro_rules ! impl_integer_functions { ( $ ( $ name : ident , $ tpe : ident ) ,* ) => { $ ( fn $ name ( & self ) -> $ tpe { * self as $ tpe } ) * } ; }
        macro_rules ! impl_integer { ( $ ( $ tpe : ident ) ,* ) => { $ ( impl Int for $ tpe { impl_integer_functions ! ( to_u8 , u8 , to_u16 , u16 , to_u32 , u32 , to_u64 , u64 , to_u128 , u128 , to_i8 , i8 , to_i16 , i16 , to_i32 , i32 , to_i64 , i64 , to_i128 , i128 , to_usize , usize , to_isize , isize ) ; fn zero ( ) -> Self { 0 } fn one ( ) -> Self { 1 } } ) * } ; }
        impl_integer!(u8, u16, u32, u64, u128, i8, i16, i32, i64, i128, usize, isize);
    }
}
pub mod scanner {
    use crate::arraylist::List;
    use std::io::{stdin, BufReader, Bytes, Read, Stdin};
    use std::str::FromStr;
    pub struct Scanner {
        buf: Bytes<BufReader<Stdin>>,
    }
    impl Scanner {
        pub fn new() -> Scanner {
            Scanner {
                buf: BufReader::new(stdin()).bytes(),
            }
        }
        pub fn read_next<T: FromStr>(&mut self) -> Option<T> {
            let token = self
                .buf
                .by_ref()
                .map(|c| c.unwrap() as char)
                .skip_while(|c| c.is_whitespace())
                .take_while(|c| !c.is_whitespace())
                .collect::<String>();
            token.parse::<T>().ok()
        }
        pub fn read_line(&mut self) -> String {
            self.buf
                .by_ref()
                .map(|c| c.unwrap() as char)
                .skip_while(|c| *c == '\n')
                .take_while(|c| *c != '\n')
                .collect()
        }
        pub fn read<T: FromStr>(&mut self) -> T {
            self.read_next().unwrap()
        }
        pub fn readn<T: FromStr>(&mut self, n: i32) -> List<T> {
            (0..n).map(|_| self.read::<T>()).collect()
        }
        pub fn chars(&mut self) -> List<char> {
            self.read::<String>().chars().collect()
        }
    }
}
pub mod misc {
    use crate::arraylist::List;
    use crate::independent::integer::Int;
    use std::collections::{BTreeSet, HashMap};
    pub const CONST_1E9_7: i64 = 1_000_000_007;
    pub fn rep<'a, S, T>(n: i32, mut f: S) -> List<T>
    where
        S: FnMut() -> T + 'a,
    {
        (0..n).map(|_| f()).collect::<List<T>>()
    }
    pub fn adjacent4(y: i32, x: i32, h: i32, w: i32) -> impl Iterator<Item = (i32, i32)> {
        const DYDX: [(i32, i32); 4] = [(-1, 0), (1, 0), (0, -1), (0, 1)];
        DYDX.iter().filter_map(move |&(dy, dx)| {
            let ny = y + dy;
            let nx = x + dx;
            if nx >= 0 && nx < w && ny >= 0 && ny < h {
                Some((ny, nx))
            } else {
                None
            }
        })
    }
    pub fn adjacent8(y: i32, x: i32, h: i32, w: i32) -> impl Iterator<Item = (i32, i32)> {
        const DYDX: [(i32, i32); 8] = [
            (-1, 0),
            (1, 0),
            (0, -1),
            (0, 1),
            (-1, -1),
            (-1, 1),
            (1, -1),
            (1, 1),
        ];
        DYDX.iter().filter_map(move |&(dy, dx)| {
            let ny = y + dy;
            let nx = x + dx;
            if nx >= 0 && nx < w && ny >= 0 && ny < h {
                Some((ny, nx))
            } else {
                None
            }
        })
    }
    pub fn run_length_encoding<T: Clone + PartialEq>(slice: &List<T>) -> List<(i64, T)> {
        slice.mirror().fold(List::new(), |mut acc, x| {
            if let Some((cnt, item)) = acc.pop() {
                if item == x {
                    acc.push((cnt + 1, x));
                } else {
                    acc.push((cnt, item));
                    acc.push((1, x));
                }
            } else {
                acc.push((1, x));
            }
            acc
        })
    }
    pub fn indices_by_elem<T: Eq + std::hash::Hash + Clone>(
        slice: &List<T>,
    ) -> std::collections::HashMap<T, List<i32>> {
        let mut hmap = std::collections::HashMap::new();
        for i in 0..slice.ilen() {
            hmap.entry(slice[i].clone()).or_insert(List::new()).push(i);
        }
        hmap
    }
    pub fn combine<S: Clone, T: Clone, U: std::iter::FromIterator<(S, T)>>(
        left: &[S],
        right: &[T],
    ) -> U {
        let mut ret = vec![];
        for i in 0..left.len() {
            for j in 0..right.len() {
                ret.push((left[i].clone(), right[j].clone()));
            }
        }
        ret.into_iter().collect::<U>()
    }
    pub fn split<T: PartialEq + Clone>(slice: &List<T>, sep: T) -> List<List<T>> {
        slice
            .iter()
            .fold(List::from(vec![List::new()]), |mut acc, x| {
                if x == &sep {
                    acc.push(List::new());
                    acc
                } else {
                    let last = acc.ilen() - 1;
                    acc[last].push(x.clone());
                    acc
                }
            })
    }
    pub fn join<T: std::fmt::Display>(slice: &List<T>, sep: &str) -> String {
        let strings = slice.iter().map(|t| format!("{}", t)).collect::<Vec<_>>();
        strings.join(sep)
    }
    pub fn coord_comp(slice: &List<i64>) -> (List<i64>, HashMap<i64, i32>) {
        let mut set = BTreeSet::new();
        for &item in slice {
            set.insert(item);
        }
        let mut hmap = HashMap::new();
        for (i, &v) in set.iter().enumerate() {
            hmap.insert(v, i as i32);
        }
        (set.into_iter().collect::<List<_>>(), hmap)
    }
    pub fn shakutori(n: i32, k: i64, a: &List<i64>) -> i32 {
        let mut sum = 0;
        let mut right = 0;
        let mut ret = 0;
        for left in 0..n {
            while right < n && sum <= k {
                sum += a[right];
                right += 1;
            }
            ret += right - left;
            if right == left {
                right += 1;
            } else {
                sum -= a[left];
            }
        }
        ret
    }
    pub fn inverse(a: &List<i32>, n: i32) -> List<i32> {
        let mut inv = List::init(0, n);
        for i in 0..a.ilen() {
            inv[a[i]] = i;
        }
        inv
    }
    pub fn pow(mut a: i64, mut n: i64) -> i64 {
        let mut res = 1;
        while n > 0 {
            if n & 1 == 1 {
                res *= a;
            }
            a = a * a;
            n >>= 1;
        }
        res
    }
    pub fn ceil_div<T: Int>(x: T, y: T) -> T {
        (x + y - T::one()) / y
    }
    pub fn ceil_mod<T: Int>(x: T, y: T) -> T {
        ceil_div(x, y) * y
    }
    pub fn unzip<P: Clone, Q: Clone>(v: &List<(P, Q)>) -> (List<P>, List<Q>) {
        (
            v.iter().map(|t| t.0.clone()).collect(),
            v.iter().map(|t| t.1.clone()).collect(),
        )
    }
    pub fn unzip3<P: Clone, Q: Clone, R: Clone>(
        v: &List<(P, Q, R)>,
    ) -> (List<P>, List<Q>, List<R>) {
        (
            v.iter().map(|t| t.0.clone()).collect(),
            v.iter().map(|t| t.1.clone()).collect(),
            v.iter().map(|t| t.2.clone()).collect(),
        )
    }
    pub fn is_palindrome<T: Clone + Eq>(chars: &List<T>) -> bool {
        let s = chars.clone();
        let mut t = s.clone();
        t.reverse();
        (0..s.ilen()).filter(|&i| s[i] == t[i]).count() as i32 == s.ilen()
    }
}
pub mod data_structure {
    pub mod counter {
        use std::collections::HashMap;
        use std::hash::Hash;
        use std::ops::*;
        #[derive(Clone, Debug)]
        pub struct Counter<K: Eq + Hash> {
            pub cnt: HashMap<K, i64>,
            pub d: i64,
        }
        impl<K: Eq + Hash> Counter<K> {
            pub fn new() -> Counter<K> {
                Counter {
                    cnt: HashMap::new(),
                    d: 0,
                }
            }
            #[doc = " Remove key when the value <= 0"]
            pub fn dec(&mut self, key: K, delta: i64) {
                if self.by_ref(&key) - delta <= 0 {
                    self.remove(&key);
                } else {
                    *self.cnt.get_mut(&key).unwrap() -= delta;
                }
            }
            pub fn by_ref(&self, key: &K) -> i64 {
                *self.cnt.get(key).unwrap_or(&self.d)
            }
        }
        impl<K: Eq + Hash> Deref for Counter<K> {
            type Target = HashMap<K, i64>;
            fn deref(&self) -> &Self::Target {
                &self.cnt
            }
        }
        impl<K: Eq + Hash> DerefMut for Counter<K> {
            fn deref_mut(&mut self) -> &mut Self::Target {
                &mut self.cnt
            }
        }
        impl<K: Eq + Hash> Index<K> for Counter<K> {
            type Output = i64;
            fn index(&self, index: K) -> &Self::Output {
                self.cnt.get(&index).unwrap_or(&self.d)
            }
        }
        impl<K: Eq + Hash + Clone> IndexMut<K> for Counter<K> {
            fn index_mut(&mut self, index: K) -> &mut i64 {
                if !self.cnt.contains_key(&index) {
                    self.cnt.insert(index.clone(), self.d);
                }
                self.cnt.get_mut(&index).unwrap()
            }
        }
        impl<K: Eq + Hash> std::iter::FromIterator<K> for Counter<K> {
            fn from_iter<T: IntoIterator<Item = K>>(iter: T) -> Self {
                let mut cnt = HashMap::new();
                for i in iter {
                    *cnt.entry(i).or_insert(0) += 1;
                }
                Counter { cnt, d: 0 }
            }
        }
        impl<T: Eq + Hash + Clone> Add for Counter<T> {
            type Output = Counter<T>;
            fn add(self, other: Counter<T>) -> Counter<T> {
                let mut ret = Counter::new();
                for (k, v) in self.iter().chain(other.iter()) {
                    ret[k.clone()] += *v;
                }
                ret
            }
        }
        impl<T: Eq + Hash + Clone> AddAssign for Counter<T> {
            fn add_assign(&mut self, other: Self) {
                *self = self.clone().add(other);
            }
        }
    }
}
pub mod ext {
    pub mod range {
        use crate::independent::integer::Int;
        use std::cmp::{max, min};
        use std::ops::{Bound, Range, RangeBounds, RangeInclusive};
        pub trait RangeEx<T> {
            fn width(&self) -> T;
            fn empty(&self) -> bool;
            fn contain_range(&self, inner: &Self) -> bool;
            fn separate_range(&self, other: &Self) -> bool;
            type ReturnRange;
            fn overlap(&self, other: &Self) -> Self::ReturnRange;
        }
        impl<T: Int> RangeEx<T> for Range<T> {
            fn width(&self) -> T {
                if self.empty() {
                    T::zero()
                } else {
                    self.end - self.start
                }
            }
            fn empty(&self) -> bool {
                !(self.start < self.end)
            }
            fn contain_range(&self, inner: &Self) -> bool {
                self.start <= inner.start && inner.end <= self.end
            }
            fn separate_range(&self, other: &Self) -> bool {
                self.end <= other.start || other.end <= self.start
            }
            type ReturnRange = Range<T>;
            fn overlap(&self, other: &Self) -> Self::ReturnRange {
                let left = max(self.start, other.start);
                let right = min(self.end, other.end);
                left..right
            }
        }
        impl<T: Int> RangeEx<T> for RangeInclusive<T> {
            fn width(&self) -> T {
                if self.empty() {
                    T::zero()
                } else {
                    *self.end() - *self.start() + T::one()
                }
            }
            fn empty(&self) -> bool {
                !(self.start() <= self.end())
            }
            fn contain_range(&self, inner: &Self) -> bool {
                self.start() <= inner.start() && inner.end() <= self.end()
            }
            fn separate_range(&self, other: &Self) -> bool {
                self.end() <= other.start() || other.end() <= self.start()
            }
            type ReturnRange = RangeInclusive<T>;
            fn overlap(&self, other: &Self) -> Self::ReturnRange {
                let left = *max(self.start(), other.start());
                let right = *min(self.end(), other.end());
                left..=right
            }
        }
        pub trait IntRangeBounds<U: Int>: RangeBounds<U> {
            #[doc = " inclusive"]
            fn lower_bound(&self, lower_bound: U) -> U {
                match self.start_bound() {
                    Bound::Included(x) => max(lower_bound, *x),
                    Bound::Excluded(x) => max(lower_bound, *x + U::one()),
                    Bound::Unbounded => lower_bound,
                }
            }
            #[doc = " exclusive"]
            fn upper_bound(&self, upper_bound: U) -> U {
                match self.end_bound() {
                    Bound::Included(x) => min(upper_bound, *x + U::one()),
                    Bound::Excluded(x) => min(upper_bound, *x),
                    Bound::Unbounded => upper_bound,
                }
            }
            fn to_harfopen(&self, lb: U, ub: U) -> Range<U> {
                self.lower_bound(lb)..self.upper_bound(ub)
            }
        }
        impl<T: ?Sized, U: Int> IntRangeBounds<U> for T where T: RangeBounds<U> {}
    }
}

0