So I'm practicing simple python as revision for school and have come across the challenge "Write an algorithm that asks the user to input a number. The program should then count from 0 and for every other number it should output "Boo".
for count in range(count,10):
print(count)
count +=2
if count % 2 == 0:
print("boo")
That is what I tried to use, I messed around with it a bit to try make it work but for some reason I just can't think of the right way.
Here is a solution:
for num in range(0, count + 1):
if num % 2 == 0:
print(num)
else:
print("boo")
Let's look at every line:
for num in range(0, count + 1):
The number on the left of range is the starting point. The number on the right is the number it counts up to.
I changed count to num to remove some confusion in the syntax. The range function creates a list of numbers from 0 to (n - 1), so I add 1 to count so it will count to n instead of n - 1.
if num % 2 == 0:
print(num)
else:
print("boo")
num % 2 checks if a number is even. 0 will technically be considered "even" because 0 % 2 = 0. Because the algorithm starts with 0, we will have this print the num, and every other num (the odd numbers) will print "boo"
Related
Although my code works, it's not the way the question wants it to be solved and I'd like to know the correct way.
The question is:
Given a sorted list of integers, output the middle integer. Assume the
number of integers is always odd.
Ex: If the input is 2 3 4 8 11 -1 (a negative indicates end), the
output is:
4 The maximum number of inputs for any test case should not exceed 9
positive values. If exceeded, output "Too many inputs".
Hint: Use an array of size 9. First, read the data into an array. Then,
based on the number of items, find the middle item.
My code:
integer userInput
integer i
integer mid
integer array(20) number
userInput = 1
for i = 0; userInput >= 0; i = i + 1
if number[i] > -1
userInput = Get next input
number[i] = userInput
i = i - 1
mid = i / 2
if i > 9
Put "Too many inputs" to output
elseif i % 2 == 0
Put number[mid - 1] to output
else
Put number[mid] to output
The problem states that the array has to be configured to a size of 9 but with 9 or 10, the program fails and I don't know why so I set it to 20 out of frustration. I've tried this problem multiple other ways like using a while loop
while number[i] > -1
but for some reason that causes it to never end even though each set of inputs does have a -1 in it. There are other ways I've forgotten but which resulted in an output of -1000000000 instead of any of the actual numbers. I'm at a loss but at least I got it working to some degree.
I asked my teacher for help and all he said was: "Your difficulty relates to your "logic" in setting up and using the array. Try starting over, from scratch"
I've started from scratch about a dozen times and I'm not seeing what he's saying. Is there some way to set up an array in Coral that I'm unaware of?
The program fails because they mandate you need to set the array to 9.
However, they sneakily input the negative number that should stop the program as the 10th input, which would act outside the array range of 9.
So the best thing to do is to set the array to the next highest odd integer: 11
Just change this line:
integer array(20) number to integer array(11) number
In case anyone else runs across this, I myself was also at the mercy of being too complex with this particular one.
Here is the Coral program for this one that passed all 10 tests
Submission passed all tests
Total score: 10 / 10
integer userInts
integer i
integer mid
integer array(9) n
userInts = Get next input
while (userInts >=0) and (i < n.size)
n[i] = userInts
userInts = Get next input
i = i + 1
if userInts >=0
Put "Too many inputs" to output
else
mid = i / 2
Put n[mid] to output
This is easier done in other languages. But this solution should work.
integer int
integer array(12) userNum
integer array(?) myArray
integer i
integer middleNum
integer counter
integer x
integer userInput
for i = 0; i < userNum.size; i = i + 1
userNum[i] = -1
userNum[0] = Get next input
for i = 0;userNum[i] >= 0; i = i + 1
userInput = Get next input
userNum[i + 1] = userInput
counter = counter + 1
if counter > 9
Put "Too many inputs" to output
else
myArray.size = counter
for i = 0; i < myArray.size; i = i + 1
myArray[i] = userNum[i]
int = myArray.size % 2
if int == 1
middleNum = myArray.size / 2
Put myArray[middleNum] to output
Backstory (not important to the question): I've got a question in one of my classes and I couldn't solve it for the past week, and I am just so stuck with it and trying to find a good solution for it, maybe it's just my limited thinking or being new to the whole recursion idea in general or new to learning the programming language we are working with (C language).
The problem: So our task is to build a "function" (I don't know the correct word for it) that for a given integer num:
if the digit is in an even index the digit in that spot has to be even.
if the digit is in an odd index the digit in that spot has to be odd.
indexes start from 0.
you can only use 1 parameter (num)
you need to return 1 if the conditions are met 0 otherwise (C language)
For example:
The number 343,418 will be a valid number because every digit in an odd index is odd and every digit in an even index is even.(the example + indexes)
The number 343,518 will be an invalid number because on the second index there is a number 5, even index odd number. (the example + indexes)
Any hints to a solution or a way to solve this will be greatly appreciated as I was trying to solve this for a while.
Here is a possible approach:
Since the one's (least significant) digit must be even, a valid number considered as a whole must also be even. So stop and return 0 if num % 2 != 0.
Get the ten's digit by tens = (num / 10) % 10, leveraging that integer division rounds down. If tens is zero, we are done validating the digits, so return 1 if tens == 0. Otherwise tens must be odd, so return 0 if tens % 2 == 0.
Now discard the bottom two digits with num /= 100 and go back to step 1.
The "go back to step 1" part could be done with a while loop or as a "tail call" if you want to express it recursively.
As suggested in the discussion in the comments, the idea here is to iterate over the digits and keep track of the index as you go, where in each step you compare the digit and index's evenness:
int compareDigitsToIndexes(int num) {
int ind = 0;
while (num > 0) {
int digit = num % 10;
if (ind % 2 != digit % 2) {
return 0;
}
num /= 10;
++ind;
}
return 1;
}
I came across a problem from a recent competition.
I was unable to figure out a solution, and no editorial for the question is yet available.
Question Link
I am quoting the problem statement here also in case the link doesn't work.
Find the number of integers n which are greater than or equal to A and less than or equal to B (A<= n <=B) and the decimal representation of 2^n ends in n.
Ex: 2^36 = 68719476736 which ends in “36”.
INPUT
The first line contains an integer T i.e. number of test cases. T lines follow, each containing two integers A and B.
Constraints
1 <= T <= 10^5
A<=B
A,B <= 10^150
OUTPUT
Print T lines each containing the answer to the corresponding testcase.
Sample Input
2
36 36
100 500
Sample Output
1
0
As often happens on programming competitions I have come up with an heuristics I have not proven, but seems plausible. I have written a short program to find the numbers up to 1000000 and they are:
36
736
8736
48736
948736
Thus my theory is the following - each consecutive number is suffixed with the previous one and only adds one digit. Hope this will set you on the right track for the problem. Note that if my assumption is right than you only need to find 150 numbers and finding each consecutive number requires checking 9 digits that may be added.
A general advice for similar problems - always try to find the first few numbers and think of some relation.
Also often it happens on a competition that you come up with a theory like the one I propose above, but have no time to prove it. You can't afford the time to prove it. Simply hope you are right and code.
EDIT: I believe I was able to prove my conjecture above(in fact I have missed some numbers -see end of the post). First let me point out that as v3ga states in a comment the algorithm above works up until 75353432948736 as no digit can be prepended to make the new number "interesting" as per the definition you give. However I completely missed another option - you may prepend some number of 0 and then add a non-zero digit.
I will now proof a lemma:
Lemma: if a1a2...an is an interesting number and n is more than 3, then a2...an also is interesting.
Proof:
2a1a2...an = 2a1*10n - 1*2a2a2...an
Now I will prove that 2a1*10n - 1*2a2a2...an is comparable to 2a2a2...an modulo 10n-1.
To do that lets prove that 2a1*10n - 1*2a2a2...an - 2a2a2...an is divisible by 10n-1.
2a1*10n - 1*2a2a2...an - 2a2a2...an =
2a2a2...an * (2a1*10n - 1 - 1)
a2a2...an is more than n-1 for the values we consider.
Thus all that's left to prove to have 10n-1 dividing the difference is that 5n-1 divides 2a1*10n - 1 - 1.
For this I will use Euler's theorem:
2phi(5n-1) = 1 (modulo 5n-1).
Now phi(5n-1) = 4*(5n-2) and for n >= 3 4*(5n-2) will divide a1*10n - 1(actually even solely 10n - 1).
Thus 2a1*10n - 1 gives remainder 1 modulo 5n-1 and so 5n-1 divides 2a1*10n - 1 - 1.
Consequently 10n-1 divides 2a2a2...an * (2a1*10n - 1 - 1) and so the last n - 1 digits of 2a1a2a2...an and 2a2a3a4...an are the same.
Now as a1a2a2...an is interesting the last n digits of 2a1a2a2...an are a1a2a2...an and so the last n-1 digits of 2a2a3a4...an are a2a3a4...an and consequently a2a3a4...an is also interesting. QED.
Use this lemma and you will be able to solve the problem. Please note that you may also prepend some zeros and then add a non-zero number.
In general, you can try solving these problems by finding some pattern in the output. Our team got this problem accepted at the contest. Our approach was to find a general pattern in the values that satisfy the criteria. If you print the first few such digits, then you will find the following pattern
36
736
8736
48736
948736
Thus the next number after 948736 should be of 7 digits and can be any one of 1948736, 2948736, 3948736, 4948736, 5948736, 6948736, 7948736, 8948736, 9948736. Thus check which value is valid and you have the next number. Continuing in this fashion you can back yourself to get all the 150 numbers.
But there is a problem here. There will be some numbers that do not immediately follow from the previous number by appending '1' to '9'. To counter this you can now start appending values from 10 to 99 and now check if there is a valid number or not. If there is still no valid number, then again try appending numbers from 100 to 999.
Now employing this hack, you will get all the 137 values that satisfy the criterion given in the question and easily answer all the queries. For example, working java code that implements this is shown here. It prints all the 137 values.
import java.io.*;
import java.math.*;
import java.util.*;
class Solution
{
public static void main(String[] args)throws java.lang.Exception{
new Solution().run();
}
void run()throws java.lang.Exception{
BigInteger[] powers = new BigInteger[152];
powers[0] = one;
for(int i=1; i<=150; i++){
powers[i] = powers[i-1].multiply(ten);
}
BigInteger[] answers = new BigInteger[152];
answers[2] = BigInteger.valueOf(36);
answers[3] = BigInteger.valueOf(736);
int last = 3;
for(int i=4; i<=150; i++){
int dif = i-last;
BigInteger start = ten.pow(dif-1);
BigInteger end = start.multiply(ten);
while(start.compareTo(end) < 0){
BigInteger newVal = powers[last].multiply(start);
newVal = newVal.add(answers[last]);
BigInteger modPow = pow(two, newVal, powers[i]);
if(modPow.equals(newVal)){
answers[i] = newVal;
System.out.println(answers[i]);
last = i;
break;
}
start = start.add(one);
}
}
}
BigInteger pow(BigInteger b, BigInteger e, BigInteger mod){
if(e.equals(zero)){
return one;
}
if(e.mod(two).equals(zero)){
BigInteger x = pow(b, e.divide(two), mod);
x = x.multiply(x).mod(mod);
return x;
}else{
BigInteger x = pow(b, e.divide(two), mod);
x = x.multiply(x).mod(mod);
x = x.multiply(two).mod(mod);
return x;
}
}
BigInteger ten = BigInteger.valueOf(10);
BigInteger zero = BigInteger.ZERO;
BigInteger one = BigInteger.ONE;
BigInteger two = BigInteger.valueOf(2);
}
This is very interesting property. During the contest, I found that 36 was the only number under 500 checking with python...
The property is : 2^36 last two digits are 36, last three digits are 736, so next number is 736. 2^736 has last three digits as 736, and next number is 8376...
And the series is : 36 , 736 , 8736 , 48736 , 948736 ...
And then started with BigInt class in C++.
But alas there was no time, and 4th problem wasn't solved. But after the contest, we did it in python.
here's link : Ideone it!
def powm(i):
j = 10
a = 1
while i:
if i % 2:
a = a * j
i /= 2
j *= j
return a
def power(n, i):
m = powm(i)
y = 1
x = 2
while n:
if n % 2 == 1:
y = y * x % m
x = x * x % m
n /= 2
return y
mylist = []
mylist.append(power(36, 2))
n = mylist[0]
print(n)
for i in range(3, 170):
p = power(n, i)
print p
if p != n:
mylist.append(p)
n = p
t = input()
while t:
x = raw_input().split(" ")
a = int(x[0])
b = int(x[1])
i = 0
#while i <= 150:
#print mylist[i]
#i += 1
#print power(8719476736,14)
while mylist[i] < a:
i += 1
ans = 0
while mylist[i] <= b:
i += 1
ans += 1
print ans
t -= 1
The final digits start to repeat after 20 increments. So for any n with the final digit 1, the final digit of the answer will be 2. So most values of n can be eliminated immediately.
2^1 = 2
2^21 = 2097152
2^101 = 2535301200456458802993406410752
2^2 = 4
2^22 = 4194304
2^42 = 4398046511104
In fact only two possibilities share a final digit:
2^14 = 16384
2^16 = 65536
2^34 = 17179869184
2^36 = 68719476736
If n is 14+20x or 16+20x, then it might work, so you'll need to check it. Otherwise, it cannot work.
I am not very good with such problems. But modular exponentiation appears to be key in your case.
Repeat for all n in the range A to B:
1. Find k, the no of digits in n. This can be done in O(logn)
2. Find 2^n (mod 10^k) using modular exponentiation and check if it is equal to n. This'll take O(n) time. (actually, O(n) multiplications)
EDIT
Actually, don't repeat the whole process for each n. Given 2^n (mod 10^k), we can find 2^(n+1) (mod 10^k) in constant time. Use this fact to speed it up further
EDIT - 2
This doesn't work for such large range.
I'm trying to understand how this code:
#include<stdio.h>
int main()
{
int j,p,k;
long long int n,i;
scanf("%lld",&n);
for(k=n;k>=1;k--)
{
p=0;
scanf("%lld",&i);
for (j=5;j<=i;j*=5)
{
p=p+i/j;
}
printf("%d\n",p);
}
return 0;
}
solves this Codechef problem: http://www.codechef.com/problems/FCTRL
What I'm having troubles understanding is how this loop works:
for (j=5;j<=i;j*=5)
{
p=p+i/j;
}
Why is the j variable set to 5 and could someone walk me trough this loop if I would give the value of 60 to the i variable?
Thanks so much!
In short the problem is to find the number of zeroes of a factorial of number between 1 to 1000000000.
Now take a pencil and a paper. Start with 1. From 1 to 4 there is no 0. First 0 occurs at 5!. The next is at 10! and then at 15!, 20!, ...... This means that number of zeroes increases at the interval of 5.
Coming to the loop
for (j=5;j<=i;j*=5)
{
p=p+i/j;
}
See the i is stand for N here (see the question). Since number of zeroes increases at the interval of 5, j is initialized to 5 and j will be incremented as a multiple of 5 .
Now the simple rule is that the number of trailing zeros in the decimal representation of N! is simply the multiplicity of the prime factor 5 in N!.
In the statement p=p+i/j;, same rule is followed. The author of the program incremented j by 5 till N/j >= 5 leaving N (i.e i) here as it is.
N = i = 30
p = 30/5 + 30/(5*5) = 6 // 30/25 is 1 and does not satisfying the condition N/j >= 5
This algorithm makes more sense if you understand the method they are using to find the number of trailing zeros of a factorial which is outlined in Trailing zero Factorial and in Factorials and Trailing Zeroes. Basically relies on the insight that you need to account for all the products of 5 and 2 in the factorial expansion to discover how many zeros there will be in the end.
The algorithm to finding the number of trailing zeros in x! boils down to to:
Finding successive powers of 5
Dividing x by the result add the truncated result to the total
Stop when the result of division is less than 1 or in this specific case we know this will happen when the result is greater than x
So if go back to the code we can find the following steps:
step 3
| step 1
V V
for (j=5;j<=i;j*=5)
{
p=p+i/j; // step 2
}
This piece of code:
p=0;
scanf("%lld",&i);
for (j=5;j<=i;j*=5)
{
p=p+i/j;
}
counts the number of factor 5 in all the integers in [1, i] and stores the result in p.
Loop 1: j=5, p+=i/5 counts numbers that are divisible by 5 in the range [1, i]
Loop 2: j=25, p+=i/25 counts numbers that are divisible by 25 in the range [1, i] (notice that such numbers have been already counted once in loop 1)
Loop 3: j=125, p+=i/125 counts numbers that are divisible by 125 in the range [1, i] (notice that such numbers have been already counted twice in loop 1 and 2)
....
I am trying to generate random number using srand and rand. Here I want to generate specific number of digit. When I am executing my program at some time if I ask to generate 5 digit number number it is not giving me desired output.
My code is
for(k=0;k<n;k++)
{
temp = temp*10;
}
srand(time(NULL));
i = rand()%temp;
printf("%d\n",i);
k = 0;
temp = n;
while(i != 0)
{
arr1[n+k] = i%10;
i = i/10;
n--;
}
Output
Number of digits you want : 5
2031
while loop 1
while loop 3
while loop 0
while loop 2
N is 1
arr1[1] = 10651312
arr1[2] = 2
arr1[3] = 0
arr1[4] = 3
arr1[5] = 1
tell me where is the problem for getting desired number of digits.
Edit
I run that code around 100 times and out of those four time it is not working, rest is fine...
The problem is you're looping on the size of the random number you've generated and not the size of the array. In your example you want five digits but your code has generated a four digit number, 2031. This means that in the iteration of your bottom loop
... n = 2, i = 2: store a[2] = 2, i = 0
... n = 1, i = 0: loop condition failed, a[1] never set
which leaves random garbage in a[1]. If your random number did in fact contain 5 digits, not 4, then it would have completed the loop correctly.
Instead you want to loop over n
for(int j = n; j > 0; --j)
{
arr1[n+j] = i%10;
i = i/10;
}
Note that this is still using the array as 1-based, whereas in c arrays are 0-based, i.e. they start at element 0, i.e. in order to use arr1[5] you need to have malloced or declared 6 array elements or 6*sizeof(int) bytes. Also note that you should use better variable names than temp, and there's no benefit to reusing the variable: your compiler will automatically reuse registers and sort that out for you.
There are several problems here.
First, call srand() once before actually producing random numbers.
Second, your method taking the returned number modulo some power of 10 will, of course, also return numbers that are lower. For example, n%100000 could be anything from 0 to 99999.
n = rand() % (largest - smallest + 1) + smallest;
If you want a 5 digit number, what is the smallest 5 digit number? Do the same for the largest number. That can be used for any number range with no need to fill an array or anything.
Now you just need to figure out how to generate the largest and smallest values for the number of digits specified.
Happy coding!