题意:

给你一个长度为n的数组,你可以对其中某个元素加上x或者减去x,这种操作你最多只能使用k次,让你输出操作后的数组,且保证这个数组所有元素的乘积尽可能小

题解:

在这之前我们要知道a*b>a*(b-x)>(a-x)*b    在a-x>0且b-x>0情况下

首先要讨论这n个元素中负数个数有多少个

1、如果负数有奇数个,那么就让绝对值靠近0的数往距离0远点(也就是负数-x,正数+x),这样操作k次后,等到的数组就满足题意

2、如果没有负数,那么首先判断可不可以让一个正数变成负数

2.1、如果可以那么找一个最小的正数变成负数之后(假设这个过程用了y次操作),然后就转化成了问题1,剩下k-y次操作让绝对值靠近0的数往距离0远点

2.2、如果不可以,那就让那个最小的正数尽可能变小

3、负数个数为偶数个,找一个绝对值最小的数,如果这个数是正数,那就把它变成负数(这个时候要看可不可以变成负数,相似于2.1,2.2);如果这个数是负数,那就把它变成正数(这个时候要看可不可以变成正数,相似于2.1,2.2)

代码:

  1 #include <iostream>
2 #include <cstdio>
3 #include <cstdlib>
4 #include <math.h>
5 #include <string.h>
6 #include <queue>
7 #include <set>
8 #include <map>
9 #include <algorithm>
10 using namespace std;
11 const int maxn=2e5+10;
12 const int inf=0x3f3f3f3f;
13 const int MAXN = 2e5+10;
14 typedef long long LL;
15 struct Node
16 {
17 int pos;
18 LL val;
19 bool operator < (const Node& that) const
20 {
21 return abs(this->val) > abs(that.val);
22 }
23 }node[MAXN];
24 int n;
25 LL k, x;
26
27 void Solve()
28 {
29 priority_queue<Node> que;
30 for (int i = 1;i <= n;i++)
31 que.push(node[i]);
32 while (k)
33 {
34 Node now = que.top();
35 que.pop();
36 if (now.val >= 0)
37 now.val += x;
38 else
39 now.val -= x;
40 que.push(now);
41 k--;
42 }
43 while (!que.empty())
44 {
45 node[que.top().pos] = que.top();
46 que.pop();
47 }
48 for (int i = 1;i <= n;i++)
49 printf("%lld ", node[i].val);
50 printf("\n");
51 }
52
53 int main()
54 {
55 scanf("%d %d %lld", &n, &k, &x);
56 int cnt = 0;
57 for (int i = 1;i <= n;i++)
58 {
59 scanf("%lld", &node[i].val);
60 node[i].pos = i;
61 if (node[i].val < 0)
62 cnt++;
63 }
64 if (cnt == 0)
65 {
66 int mpos = 1;
67 for (int i = 1;i <= n;i++)
68 {
69 if (node[i].val < node[mpos].val)
70 mpos = i;
71 }
72 LL ti = (node[mpos].val+1LL+x-1)/x;
73 if (ti > k)
74 node[mpos].val -= k*x;
75 else
76 node[mpos].val -= ti*x;
77 k -= min(ti, k);
78 }
79 else if (cnt > 0 && cnt%2 == 0)
80 {
81 int mpos = 1;
82 for (int i = 1;i <= n;i++)
83 {
84 if (abs(node[i].val) < abs(node[mpos].val))
85 mpos = i;
86 }
87 if (node[mpos].val >= 0)
88 {
89 LL ti = (node[mpos].val+1LL+x-1)/x;
90 if (ti > k)
91 node[mpos].val -= k*x;
92 else
93 node[mpos].val -= ti*x;
94 k -= min(ti, k);
95 }
96 else
97 {
98 LL ti = (abs(node[mpos].val)+1LL+x-1)/x;
99 if (ti > k)
100 node[mpos].val += k*x;
101 else
102 node[mpos].val += ti*x;
103 k -= min(ti, k);
104 }
105 }
106 Solve();
107
108 return 0;
109 }

优先队列排序情况:

 1 #include <bits/stdc++.h>
2 using namespace std;
3 typedef long long LL;
4 const int MAXN = 2e5+10;
5 struct Node
6 {
7 int pos;
8 LL val;
9 bool operator < (const Node& that) const
10 {
11 return abs(this->val) > abs(that.val); //这个时候优先队列从小到大排序
12 //return abs(this->val) < abs(that.val); //这个时候优先队列从大到小排序
13 //return abs(that.val) > abs(this->val); //这个时候优先队列从大到小排序
14 //return abs(that.val) < abs(this->val); //这个时候优先队列从小到大排序
15 }
16 }node[MAXN],str1;
17 int main()
18 {
19 priority_queue<Node>r;
20 str1.val=1;
21 r.push(str1);
22 str1.val=2;
23 r.push(str1);
24 str1.val=3;
25 r.push(str1);
26 while(!r.empty())
27 printf("%d ",r.top().val),r.pop();
28 return 0;
29 }

CodeForces - 721D 贪心+优先队列(整理一下优先队列排序情况)的更多相关文章

  1. Codeforces 898 贪心关闭最少闹钟 优先队列最少操作构造N/2squares 讨论情况哈希数字串分割a+b=c

    A /* Huyyt */ #include <bits/stdc++.h> #define mem(a,b) memset(a,b,sizeof(a)) #define mkp(a,b) ...

  2. Codeforces 721D [贪心]

    /* 不要低头,不要放弃,不要气馁,不要慌张. 题意: 给一列数a,可以进行k次操作,每次操作可以选取任意一个数加x或者减x,x是固定的数.求如何才能使得这个数列所有数乘积最小. 思路: 贪心...讨 ...

  3. Maxim and Array CodeForces - 721D (贪心)

    大意: 给定序列, 每次操作选择一个数+x或-x, 最多k次操作, 求操作后所有元素积的最小值 贪心先选出绝对值最小的调整为负数, 再不断选出绝对值最小的增大它的绝对值 #include <io ...

  4. C - Ordering Pizza CodeForces - 867C 贪心 经典

    C - Ordering Pizza CodeForces - 867C C - Ordering Pizza 这个是最难的,一个贪心,很经典,但是我不会,早训结束看了题解才知道怎么贪心的. 这个是先 ...

  5. POJ - 3190 Stall Reservations 贪心+自定义优先级的优先队列(求含不重叠子序列的多个序列最小值问题)

    Stall Reservations Oh those picky N (1 <= N <= 50,000) cows! They are so picky that each one w ...

  6. Codeforces 677D - Vanya and Treasure - [DP+优先队列BFS]

    题目链接:http://codeforces.com/problemset/problem/677/D 题意: 有 $n \times m$ 的网格,每个网格上有一个棋子,棋子种类为 $t[i][j] ...

  7. [luoguP2672] 推销员(贪心 + 树状数组 + 优先队列)

    传送门 贪心...蒟蒻证明不会... 每一次找最大的即可,找出一次最大的,数列会分为左右两边,左边用stl优先队列维护,右边用树状数组维护.. (线段树超时了....) 代码 #include < ...

  8. codeforces 1283F. DIY Garland(树+优先队列)

    题目连接:https://codeforces.com/contest/1283/problem/F 题意:一根电线连接着两个点,这两个点分别代表着两个灯,灯有自己的编号i,其亮度是2 ^ i,每根电 ...

  9. Codeforces Beta Round #94 div2 D 优先队列

    B. String time limit per test 2 seconds memory limit per test 256 megabytes input standard input out ...

随机推荐

  1. python学习笔记 | wordcloud安装指南

    问题: 直接在命令行输入: pip install wordcloud 不出意外,直接报错,显示缺失vc*****.bat,意思是缺失vc版本,这个安装方式基本可以扔掉. 解决: http://t.c ...

  2. Linux面试必备

    1.Linux的体系结构

  3. 负载均衡和故障转换(Failover)的连接RAC方法

    TAF:Transparent Application Failover,透明的应用切换,即在切换的过程中,用户感知不到.可以实现会话的切换(无法实现事务的切换,即没有提交的事务会回滚),即在不断开连 ...

  4. bean与map之间的转化

    import java.util.HashMap; import java.util.Map; import org.apache.commons.beanutils.BeanUtils; impor ...

  5. pytorch——合并分割

    分割与合并 import torch import numpy as np #假设a是班级1-4的数据,每个班级里有32个学生,每个学生有8门分数 #假设b是班级5-9的数据,每个班级里有32个学生, ...

  6. Supporting Multiple Versions of WebSocket Protocol 支持多版本WebSocket协议

    https://tools.ietf.org/html/rfc6455#section-4.4 4.4. Supporting Multiple Versions of WebSocket Proto ...

  7. 流量染色与gRPC服务托管 微服务协作开发、灰度发布之流量染色 灰度发布与流量染色

    大规模微服务场景下灰度发布与流量染色实践 https://mp.weixin.qq.com/s/UBoRKt3l91ffPagtjExmYw [go-micro]微服务协作开发.灰度发布之流量染色 - ...

  8. 自修改代码 on the fly 动态编译 即时编译 字节码

    https://zh.wikipedia.org/wiki/自修改代码 自修改代码(Self-modifying code)是指程序在运行期间(Run time)修改自身指令.可能的用途有:病毒利用此 ...

  9. 一个实体对象不能由多个 IEntityChangeTracker 实例引用

    因为需求需要EF 实现批量的删除后插入,所以出现了这个报错, 这个报错的原因是,EF查询是有带跟踪的,跟踪后其他上下文想操作这个实体就会报错. 所以,查询使用 ef AsNoTracking 查后无追 ...

  10. CF1190B

    扯在前面 我们老师刚讲过的题目,很考验思维,本蒟蒻WA了十发才过,然后看到题解里只是指出了特殊情况没多解释,可能有人看不懂,特来分享一下 首先题目就很有意思,思考的过程也很有趣,想把所有情况思考全思考 ...