AtCoder Beginner Contest 167 B問題「Easy Linear Programming」の解説を行います。
問題概要
$1$が書かれたカードが$A$枚、$0$が書かれたカードが$B$枚、$-1$が書かれたカードが$C$枚存在する。
これらのカードからちょうど$K$枚を選んで取るとき取ったカードに書かれた数の和として、ありうる最大値はいくつか答えよ。
制約
・入力は全て整数
・$0 \leq A,B,C$
・$1 \leq K \leq A+B+C \leq 2×10^9$
解説
最大値を可能な限り大きくするため$K$の値によってカードの取り方を以下のようにします。
1.$K \leq A$の場合
$K$枚の$1$が書かれたカードを選んで取れば良いです。
2.$A < K \leq A+B$の場合
1.で示した取り方を行った後に、残りの$(K-A)$枚の$0$が書かれたカードを選んで取れば良いです。
3.$A+B < K \leq A+B+C$の場合
2.で示した取り方を行った後に、残りの$(K-A-B)$枚の$-1$が書かれたカードを選んで取れば良いです。
1.の場合答えは$K$
2.の場合答えは$A$
3.の場合答えは$A-(K-A-B)$
となります。
$K$の値によって答えの出力を変えれば良いです。
なお、制約が
$A+B+C \leq 2×10^9$
となっていますが、
一般的なint
型(C++やJava)で表せる数値の範囲は
$-2^{31}$~$2^{31}-1$まであり、
$2^{31} = 21474883647$であることから、
制約内では、$K$はint
型で定義しても問題はないでしょう。
以下、Python3,C++,Javaでの解答例を示します。
各言語解答例
Python3での解答例
A,B,C,K = map(int,input().split())
if (K <= A):
print(K)
elif (A < K <= A+B):
print(A)
else:
print(A-(K-A-B))
C++での解答例
#include<bits/stdc++.h>
using namespace std;
int main(){
int a,b,c,k;
cin >> a >> b >> c >> k;
if (k <= a){
cout << k << endl;
}else if (k <= a+b){
cout << a << endl;
}else{
cout << a-(k-a-b) << endl;
}
}
Javaでの解答例
import java.util.Scanner;
public class Main{
public static void main(String[] args){
Scanner scan = new Scanner(System.in);
int a = scan.nextInt();
int b = scan.nextInt();
int c = scan.nextInt();
int k = scan.nextInt();
if (k <= a){
System.out.println(k);
}else if (k <= a+b){
System.out.println(a);
}else{
System.out.println(a-(k-a-b));
}
}
}