USACO 2016 February · Bronze · all three problems

← Full February 2016 set · Official results

Source. Statements and constraints below are paraphrased from usaco.org/index.php?page=feb16results. Each problem heading links to the canonical statement on usaco.org. Code is my own reference C++ — cross-check the official editorial before trusting it under contest pressure.

Problem 1 — Milk Pails

Statement

Farmer John has a big pail of capacity M and two small pails of capacities X and Y (X < Y < M). He may repeatedly pick one of the two small pails, fill it completely, and pour it into the big pail — but only if doing so does not cause the big pail to overflow. Maximize the amount of milk in the big pail.

Constraints

Key idea

Try every combination (a, b) where a is the number of X-pours and b is the number of Y-pours, with a·X + b·Y ≤ M. Since X ≥ 1, a ≤ M and b ≤ M, so the search space is at most ~M² = 106. Track the maximum a·X + b·Y achieved.

Complexity target

O(M²) time, O(1) memory. Comfortably under the 2s limit.

Reference solution (C++)

#include <bits/stdc++.h>
using namespace std;

int main() {
    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);
    int X, Y, M;
    cin >> X >> Y >> M;
    // Try a fills of X-pail and b fills of Y-pail; constraint a*X + b*Y <= M.
    int best = 0;
    for (int a = 0; a * X <= M; ++a) {
        int rem = M - a * X;
        int b = rem / Y;             // largest b with b*Y <= rem
        int total = a * X + b * Y;
        best = max(best, total);
    }
    cout << best << "\n";
}

Pitfalls

Problem 2 — Circular Barn

Statement

A circular barn has n rooms in a ring. Room i needs exactly ri cows. Farmer John unlocks exactly one exterior door; every cow enters through that door and walks clockwise to her room. Choose the door to minimize the total walking distance summed over all cows.

Constraints

Key idea

For a fixed entry door s, a cow heading to room (s+k) mod n walks k doors. Total cost from door s is Σk=0..n−1 k · r(s+k) mod n. With n ≤ 1000, try all n candidate doors and compute each sum in O(n). O(n²) ≈ 106 is comfortable.

Complexity target

O(n²) time, O(n) memory.

Reference solution (C++)

#include <bits/stdc++.h>
using namespace std;
using ll = long long;

int main() {
    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);
    int n; cin >> n;
    vector<ll> r(n);
    for (auto& x : r) cin >> x;

    ll best = LLONG_MAX;
    for (int s = 0; s < n; ++s) {
        ll cost = 0;
        for (int k = 0; k < n; ++k) {
            cost += (ll)k * r[(s + k) % n];
        }
        best = min(best, cost);
    }
    cout << best << "\n";
}

Pitfalls

Problem 3 — Load Balancing

Statement

N cows sit at distinct points (xi, yi) with xi, yi positive odd integers. Place a vertical fence x = a and a horizontal fence y = b with a, b even integers, splitting the plane into four quadrants. Let M be the maximum number of cows in any of the four regions. Minimize M.

Constraints

Key idea

The only candidate fence positions that matter are between consecutive cow coordinates. With N ≤ 100, there are at most N+1 useful values of a and N+1 of b. For each (a, b) pair, count cows in each quadrant in O(N). Total: O(N³) ≈ 106, trivially fast.

Complexity target

O(N³) time, O(N) memory.

Reference solution (C++)

#include <bits/stdc++.h>
using namespace std;

int main() {
    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);
    int N, B; cin >> N >> B;
    vector<int> X(N), Y(N);
    for (int i = 0; i < N; ++i) cin >> X[i] >> Y[i];

    // Candidate fence values: just below each cow's x (and y). x_i is odd, x_i - 1 is even.
    vector<int> xs = X, ys = Y;
    sort(xs.begin(), xs.end()); xs.erase(unique(xs.begin(), xs.end()), xs.end());
    sort(ys.begin(), ys.end()); ys.erase(unique(ys.begin(), ys.end()), ys.end());

    int best = N;
    for (int xi : xs) for (int yi : ys) {
        // Fence at a = xi - 1, b = yi - 1 (both even). Quadrants: x < a, x > a × y < b, y > b.
        int q[4] = {0,0,0,0};
        for (int i = 0; i < N; ++i) {
            int r = (X[i] > xi - 1) * 2 + (Y[i] > yi - 1);
            q[r]++;
        }
        best = min(best, max({q[0], q[1], q[2], q[3]}));
    }
    cout << best << "\n";
}

Pitfalls

What Bronze February 2016 was actually testing