2019.03.16【NOIP提高组】模拟 B 组 电费结算(electric)

本文介绍了一种简单的算法,用于计算在已知总电费和两人电费差额的情况下,如何确定个人需支付的具体电费金额。

JZOJ3018. 电费结算(electric)

Description

WZK最近靠租房发家致富了。作为WZK老同学的你也要租房,于是WZK决定不要房租,但是电费还得付。以下是用电价格:

在这里插入图片描述

举个例子吧。如果你用电为10123千瓦时,那么要付2 * 100 + 3 * 9900 + 5 * 123 = 30515块钱(好贵)。

到结算电费的日子了,可是WZK家里只有一个总电表,也就是统计你和WZK总共用的电量。但是WZK有办法告诉你以下信息:

1).如果按照总电表来看要交给供电局的钱A。(也就是两个人用电量加起来一起算钱)

2).你和WZK如果分开付的话,你们付的钱的差值B。

现在你想知道如果你单独算钱的话,需要付多少钱。当然,你的用电量不会比WZK多。

举个例子:如果你们一起算钱要付1100,并且如果分开来算,你们的差值是300的话,那么你用了150kwh,WZK用了250kwh。让我们来验算一下:你们一共用电400kwh,所以要付2 * 100 + 3 * 300 = 1100,你单独要付2 * 100 + 3 * 50 = 350,WZK单独要付2 * 100 + 3 * 150 = 650。所以最后,你只需要告诉我你单独要付350元。

Input

输入仅一行,包含两个整数A和B(1 ≤ A, B ≤ 10^9),含义同上。 输出描述: 输出仅一行一个整数,代表你单独算需要付的钱。数据保证解唯一。

Output

输出仅一行一个整数,代表你单独算需要付的钱。数据保证解唯一。

Sample Input

1100 300

Sample Output

350

Data Constraint

Solution

水题一道
考场AC
这道题很简单,只需要用a算出两人一共用的电量,然后二分自己的电量即可。
好像可以暴力过

Code

#include<bits/stdc++.h>
#define open_in(x) freopen(""#x".in","r",stdin);
#define open_out(x) freopen(""#x".out","w",stdout);
#define open_(x) freopen(""#x".in","w",stdout);
#define open(x) open_in(x);open_out(x);
#define mes(x,y) memset(x,y,sizeof(x));
#define mec(x,y) memcpy(x,y,sizeof(x));
using namespace std;
typedef long long ll;
typedef double db;
typedef unsigned long long ull;
const int X=-1;
const int M=1e9+7;

int Random(int x,int y){return rand()%(y-x+1)+x;}

inline int max(int x,int y){return x>y?x:y;}
inline int min(int x,int y){return x<y?x:y;}

inline void read(int &x)
{
	int f=1;char ch=getchar();x=0;
	while (ch<'0' || ch>'9'){if (ch=='-') f=-1;ch=getchar();}
	while (ch>='0' && ch<='9'){x=x*10+ch-'0';ch=getchar();}
	x*=f;
}

const int V[5]={0,2,3,5,7},N[4]={0,100,10000,1000000},P[4]={0,200,29900,4979900};

int a,b,ans,xy;

int M_S(int a)
{
	if (a<=P[1]) return a/V[1];
	if (a<=P[2]) return (a-P[1])/V[2]+N[1];
	if (a<=P[3]) return (a-P[2])/V[3]+N[2];
	return (a-P[3])/V[4]+N[3];
}

int S_M(int a)
{
	if (a<=N[1]) return a*V[1];
	if (a<=N[2]) return (a-N[1])*V[2]+P[1];
	if (a<=N[3]) return (a-N[2])*V[3]+P[2];
	return (a-N[3])*V[4]+P[3];
}

int main()
{
	open(electric);
	read(a),read(b);
	xy=M_S(a);
	for (int l=0,r=xy/2,mid=r/2;l<=r;mid=(l+r)/2)
	{
		int c=S_M(xy-mid)-S_M(mid);
		if (c<=b)
			r=(ans=mid)-1;
		else
			l=mid+1;
	}
	printf("%d\n",S_M(ans));
	return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值