Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- namespace Bitwise_Operations
- {
- using System;
- public class EmergencyRepairs
- {
- public static void Main(string[] args)
- {
- ulong wall = ulong.Parse(Console.ReadLine());
- int emergencyKits = int.Parse(Console.ReadLine());
- int attacksCount = int.Parse(Console.ReadLine());
- /* An attack means unsetting a bit at a specified position;
- * there is a formula for that: number &= ~ (1 << p) */
- for (int i = 0; i < attacksCount; i++)
- {
- int position = int.Parse(Console.ReadLine());
- wall &= ~(1ul << position);
- }
- // Used to keep track of 0s we turned into 1s
- bool previousWasZero = false;
- /* Border case, check if first bit (position 0) is part of a hole;
- * 3 is 11 in binary, so we check if both bit 0 and 1 are empty
- * which means bit 0 is part of a hole. We also check if we have
- * repair kits available in order to plug the hole. */
- if ((wall & 3) == 0 && emergencyKits > 0)
- {
- wall |= 1; // repair it, simply set bit 0 to 1
- emergencyKits--; // remember to keep track of repair kits
- // since we turned a 0 into 1, when we move on we need to know there used to be a 0 here
- previousWasZero = true;
- }
- // iterate bits from 1 to 62; border cases (bits 0 and 63) are taken care of separately
- for (int position = 1; position < 63; position++)
- {
- int bit = (int)((wall >> position) & 1); // What's the value of the current bit?
- if (bit == 1)
- {
- // Mark that the 1 we have wasn't a 0 we repaired and move on to next position
- previousWasZero = false;
- continue;
- }
- /* Take the value of the bit we're currently at along with its two neighbors;
- * 7 is 111 in binary, so this masks out all other bits but the three we care about */
- int triplet = (int)((wall >> (position - 1)) & 7);
- /* We have a hole if the triplet is something different than 101 in binary (5) or
- * if it is 101, but the 1 to the right used to be a 0 we repaired. Remember to check
- * if we have enough repair kits. */
- if ((triplet != 5 || previousWasZero) && emergencyKits > 0)
- {
- wall |= 1ul << position; // repair bit - set it to 1
- emergencyKits--; // Keep track of repair kits
- // Exit if we don't have any more kits left
- if (emergencyKits == 0)
- {
- break;
- }
- /* We turned a 0 into 1, we need to save this information in case the
- * bit to the left is 0 and the one next to it is 1. */
- previousWasZero = true;
- }
- }
- // Border case - check bit at position 63
- int lastBit = (int)((wall >> 63) & 1);
- if (lastBit == 0 && previousWasZero && emergencyKits > 0)
- {
- wall |= 1ul << 63;
- }
- Console.WriteLine(wall);
- }
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement