example1/
example1.rs

1use rand::Rng;
2use std::path::PathBuf;
3
4const SOLUTION: &str = r#"
5#include<iostream>
6using namespace std;
7
8int main(){
9    int n;
10    cin>>n;
11    long long sum=0;
12    int big=0;
13    while(n--){
14        int a;
15        cin>>a;
16        big=max(big,a);
17        sum+=a;
18    }
19    cout<<sum-big/2<<"\n";
20}
21"#;
22
23const PARTIAL_SOLUTION: &str = r#"
24#include<iostream>
25using namespace std;
26
27int main(){
28    int n;
29    cin>>n;
30    int x;
31    cin>>x;
32    cout<<x/2<<"\n";
33}
34"#;
35
36fn main() {
37    // The first task you get an array of integers. You need to find the sum of all elements in the array minus the half of the maximum element.
38    // Also all elements in the array are even.
39
40    let mut task = ezcp::Task::new("Coupon", &PathBuf::from("task1"));
41    //task.debug_level = LevelFilter::Trace;
42
43    task.solution_source = SOLUTION.to_owned();
44
45    // Constraint: n = 1
46    let mut subtask1 = ezcp::Subtask::new();
47
48    // This checker is optional and can be omitted.
49    subtask1.set_checker(|mut input| {
50        // read an array from input
51        let array = input.get_array()?;
52        // expect end of input
53        input.expect_end()?;
54        let n = array.len();
55        if n != 1 {
56            ezcp::bail!("n should be 1");
57        }
58        // check if the only value is even
59        if array[0] % 2 != 0 {
60            ezcp::bail!("all array values should be even");
61        }
62        // check if the only value is in range
63        if !(0..=1_000_000_000).contains(&array[0]) {
64            ezcp::bail!("all array values should be in range [0, 1_000_000_000]");
65        }
66        Ok(())
67    });
68
69    // add 5 tests where an array is generated with length 1 and even values between 0 and 1_000_000_000 (inclusive)
70    subtask1.add_test(5, ezcp::array_generator_custom(1, 1, |rng| rng.random_range(0..=500_000_000) * 2));
71    // this is a faulty test for testing the checker
72    //subtask1.add_test_str("1\n 0 0\n".to_owned());
73
74    // Constraint: all values are the same
75    let mut subtask2 = ezcp::Subtask::new();
76
77    subtask2.set_checker(|mut input| {
78        let array = input.get_array()?;
79        input.expect_end()?;
80        let n = array.len();
81        if !(1..=200_000).contains(&n) {
82            ezcp::bail!("n should be in range [1, 200_000]");
83        }
84        let x = array[0];
85        for i in array {
86            if i != x {
87                ezcp::bail!("all array values should be the same");
88            }
89            if i % 2 != 0 {
90                ezcp::bail!("all array values should be even");
91            }
92            if !(0..=1_000_000_000).contains(&i) {
93                ezcp::bail!("all array values should be in range [0, 1_000_000_000]");
94            }
95        }
96        Ok(())
97    });
98
99    // add 5 random tests where each test is an array of length between 1 and 200_000 (inclusive) and all values are the same even value between 0 and 1_000_000_000 (inclusive)
100    subtask2.add_test(5, || {
101        let mut rng = rand::rng();
102        let n = rng.random_range(1..=200_000);
103        let x = rng.random_range(0..=500_000_000) * 2;
104        ezcp::array_to_string(&vec![x; n as usize], true)
105    });
106
107    // add an edge case where n is maximal
108    let mut rng = rand::rng();
109    let x = rng.random_range(0..=500_000_000) * 2;
110    subtask2.add_test_str(ezcp::array_to_string(&vec![x; 200_000], true));
111
112    // add 3 edge cases where all values are maximal
113    subtask2.add_test(3, ezcp::array_generator(1, 200_000, 1_000_000_000, 1_000_000_000));
114
115    // add an edge case where all values and n are maximal
116    subtask2.add_test_str(ezcp::array_to_string(&vec![1_000_000_000; 200_000], true));
117
118    // No additional constraints
119    let mut subtask3 = ezcp::Subtask::new();
120
121    subtask3.set_checker(|mut input| {
122        let array = input.get_array()?;
123        input.expect_end()?;
124        let n = array.len();
125        if !(1..=200_000).contains(&n) {
126            ezcp::bail!("n should be in range [1, 200_000]");
127        }
128        for i in array {
129            if i % 2 != 0 {
130                ezcp::bail!("all array values should be even");
131            }
132            if !(0..=1_000_000_000).contains(&i) {
133                ezcp::bail!("all array values should be in range [0, 1_000_000_000]");
134            }
135        }
136        Ok(())
137    });
138
139    // add some random tests
140    subtask3.add_test(5, ezcp::array_generator_custom(1, 200_000, |rng| rng.random_range(0..=500_000_000) * 2));
141
142    // add 5 edge cases where n is maximal (other edge cases are handled by subtask2)
143    subtask3.add_test(5, ezcp::array_generator_custom(200_000, 200_000, |rng| rng.random_range(0..=500_000_000) * 2));
144
145    // add subtasks to task
146    let subtask1 = task.add_subtask(subtask1);
147    let subtask2 = task.add_subtask(subtask2);
148    let subtask3 = task.add_subtask(subtask3);
149
150    // add dependencies (dependencies are only if constraints of a dependency are a subset of constraints of a subtask)
151    task.add_subtask_dependency(subtask3, subtask1);
152    task.add_subtask_dependency(subtask3, subtask2);
153
154    // there is a partial solution that only reads 2 integers: n, x and prints x / 2 which is correct for subtask1 but should fail for subtask2 and subtask3
155    task.add_partial_solution(PARTIAL_SOLUTION.to_owned(), &[subtask1]);
156
157    // finally create the tests
158    task.create_tests().ok();
159}