AtCoderのABC
次のABCの問題へ
前のABCの問題へ
ABC340-D Only one of two
C#のソース
using System;
using System.Collections.Generic;
using System.Linq;
class Program
{
static string InputPattern = "InputX";
static List<string> GetInputList()
{
var WillReturn = new List<string>();
if (InputPattern == "Input1") {
WillReturn.Add("2 3 5");
//9
}
else if (InputPattern == "Input2") {
WillReturn.Add("1 2 3");
//5
}
else if (InputPattern == "Input3") {
WillReturn.Add("100000000 99999999 10000000000");
//500000002500000000
}
else {
string wkStr;
while ((wkStr = Console.ReadLine()) != null) WillReturn.Add(wkStr);
}
return WillReturn;
}
static long mA;
static long mB;
static long mK;
static long LCM;
static void Main()
{
List<string> InputList = GetInputList();
long[] wkArr = InputList[0].Split(' ').Select(pX => long.Parse(pX)).ToArray();
mA = wkArr[0];
mB = wkArr[1];
mK = wkArr[2];
LCM = DeriveLCM2(mA, mB);
long L = 0;
long R = long.MaxValue;
while (L + 1 < R) {
long Mid = R / 2;
if (R < long.MaxValue) {
Mid = (L + R) / 2;
}
long ProdCnt = GetProdCnt(Mid);
if (ProdCnt >= mK) {
R = Mid;
}
else {
L = Mid;
}
}
Console.WriteLine(R);
}
// Valを引数として、Val以下で、公倍数以外の倍数の個数を求める
static long GetProdCnt(long pVal)
{
long Cnt1 = pVal / mA;
long Cnt2 = pVal / mB;
long Cnt3 = pVal / LCM;
return Cnt1 + Cnt2 - Cnt3 * 2;
}
// 2つの数のLCMを求める
static long DeriveLCM2(long p1, long p2)
{
long GCD = DeriveGCD(p1, p2);
return (p1 / GCD) * p2;
}
// ユークリッドの互除法で2数の最大公約数を求める
static long DeriveGCD(long pVal1, long pVal2)
{
long WarareruKazu = pVal2;
long WaruKazu = pVal1;
while (true) {
long Amari = WarareruKazu % WaruKazu;
if (Amari == 0) return WaruKazu;
WarareruKazu = WaruKazu;
WaruKazu = Amari;
}
}
}
解説
答えを二分探索してます。
LCMの倍数以外の倍数の個数は、ベン図を書けば分かります。