We want to find the number of 'a's in a given string s multiplied infinite times.
We will be given a number n that is the slicing size of the infinite string.
sample input:
aba 10
output:
7
Here aba is multiplied with 10, resulting in 'abaabaabaa'
and the no. of 'a's are 7.
This is my code:
def repeatedString(s, n):
count = 0
inters = s * n
reals = s[0:n+1]
for i in reals:
if (i == 'a'):
count += 1
return count
I'm getting 2 instead of 7 as the output (test case 'aba' 10). Where did I go wrong? I just multiplied the given string with n because it will never be greater than the slicing size.
Here's the link to the problem:
https://www.hackerrank.com/challenges/repeated-string/problem
Much simpler solution using python3.
s = input().strip()
n = int(input())
print(s[:n%len(s)].count('a')+(s.count('a')*(n//len(s))))
There's no reason to slice the string
def repeatedString(s, n):
count = 0
for index, i in enumerate(s*n):
if index >= n:
return count
if(i == 'a'):
count += 1
# empty string
return count
I used a simple unitary method.
Number of 'a' in one repetition is cnt_a so the number of 'a' in first n characters will be (cnt_a/len(s)) * n
def repeatedString(s, n):
if len(s)==1 and s=='a':
return n
cnt_a=0
for i in s:
if i == 'a':
cnt_a+=1
if cnt_a % 2 == 0:
no_a = (cnt_a/len(s)) * n
return math.ceil(no_a)
else:
no_a = (cnt_a/len(s)) * n
return math.floor(no_a)
If you would like a more readable answer....
def repeatedString(s, n):
target = 'a'
target_count = 0
# how many times does the string need to be repeated: (n // len(s) * s) + s[:(n % len(s))]
quotient = n // len(s)
remainder = n % len(s)
for char in s: # how many times target appears in 1 instance of the substring
if char == target:
target_count += 1
# how many times the target appears in many instances of the substring provided
target_count = target_count * quotient
for char in s[:remainder]: # count the remaining targets in the truncated substring
if char == target:
target_count += 1
return target_count
One liner answer:
return [s[i%len(s)] for i in range(n)].count('a')
There is only two problem in your code
s = 'aba'
n = 10
count = 0
inters = s * n
# Here you need to slice(inters) not (s) because s only hold 'aba'
# And not n+1 it's take 11 values only n
reals = inters[0:n]
for i in reals:
if (i == 'a'):
count += 1
print(count)
so if the string contains "a"s only simply return n. otherwise, count the number of a's in the string s, now using divmond() function I have found the number of string that can be added without surpassing n. for example string s is "aba" and n=10, so I can add 3 "abs"s completely without the length of string going over 10. now the number of a's in the added string (3*2). Now the places left to be filled are equal to the remainder(y) of divmond() function. Now slice the string s up to y and find the number of a's in it and add it to count.
divmond(10,3) returns (10//3) and it's remainder.
def repeatedString(s, n):
if len(s)==1 and s=="a":
return n
count=s.count("a")
x,y=divmod(n,len(s))
count=count*x
str=s[:y]
return count+str.count("a")
The solution in Python 3:
def repeatedString(s,n):
i = 0
c = 0
for i in s:
if i == 'a':
c += 1
q = int(n / len(s)) #Finding the quotient
r = int(n % len(s)) #Finding the remainder
if r == 0:
c *= q
else:
x = 0
for i in range(r):
if s[i] == 'a':
x += 1
c = c*q + x
return int(c)
s = input()
n = int(input())
print(repeatedString(s,n))
if character 'a' is present in a given string pattern, then its quite faster to get the repeated count for it and later based on the total length of final string mentioned, will be trying to repeat the given pattern for same number of times & hence will multiple the repeated count with number of times a string pattern is going to repeat. Importantly if final string input is in odd numbers then we need to identify the those odd pattern and separately count the occurance of character 'a' in odd string pattern. Finally summing up the total count ( even & odd ) will gives us the expected result
def repeatedString(s, n):
# Get the length of input string
strlen = len(s)
a_repeat = 0
# Get the total count of a repeated character from the input string
for i in range(0,strlen):
if s[i] == 'a':
a_repeat = a_repeat + 1
# Get the multiplier to make sure that desired input string length achieved
str_multiplier = int(n // strlen)
# Get the repeated count if new string is been created
result = a_repeat*str_multiplier
new_str = s[:int( n % strlen )]
# for odd length of string, get the remaining characters and find repated characters count and add up it to final count
for i in range(0, len(new_str)):
if new_str[i] == 'a':
result += 1
return result
For this problem,
Get the length of string s.
First, if conditions: constrain
Now, instead of using a loop to add to space and time complexity, we use basic math's. Find the quotient of n//Len (s). Now find the number of times "a" is used in our string.
We can multiply the quotient with this number to get the total "a" used. Now, we can find the remainder of the string and use slice to search for "a" in the string we have left in the last.
Add both to get our answer.
def repeatedString(s, n):
#finding quotient and remainder of division
str1=len(s)
remainder=0
if 1<=str1<=100 and 1<=n<=10**12:
quotient= n//str1
a_s = s.count("a")
if a_s==0:
return 0
else:
remainder=s[:n%str1].count('a')
return quotient*a_s + remainder
Simple answer:
def repeatedString(s, n):
totalNumber = 0 // setting total of a's to 0
// using count function to find the total number of a's in the substring
totalNumber = s.count('a')
// finding how many number of times the substring fits in "n" and multiplying that by the number of a's we found earlier
totalNumber = n//len(s) * totalNumber
// if there is a remainder, we loop through the remainder string and add the number of "a's" found in that substring to the total
for i in s[:n%len(s)]:
if(i == "a"):
totalNumber +=1
return totalNumber
Related
Write a function that takes an array/list of numbers and returns a number.
See the examples and try to guess the pattern:
even_odd([1,2,6,1,6,3,1,9,6]) => 393
even_odd([1,2,3]) => 5
even_odd([0,2,3]) => 3
even_odd([1,0,3]) => 3
even_odd([3,2]) => 6
def even_odd(arr):
count = 0
index = 0
length = len(arr)
while index < length:
for num in range(len(arr)):
if arr[index] % 2 != 0:
count += arr[index]
index += 1
else:
count *= arr[index]
index += 1
return count
So basically the pattern is multiply the first 2 numbers and add the third and I set it to where for each index value if it it was the first number I would add it to the count to keep track and then multiply it with the second number and then add the third. I passed 3/4 sample cases except for one which was the first one ---> even_odd([1,2,6,1,6,3,1,9,6]) => 393. I am just wondering what is the flaw with my logic and does anyone have a better way to solve this that is efficient and clean.
Your question is a challenge on Codewars (https://www.codewars.com/kata/559e708e72d342b0c900007b), so maybe you should use this platform to discuss solutions with other competitiors, instead of Stackoverflow.
The main point of this challange is to investigate the calculated pattern and not the code itself.
If you know the required pattern, the code is easy (Spoiler!):
def even_odd(arr):
num = 0
for i, e in enumerate(arr):
if (i % 2) == 0:
num += e
else:
num *= e
return num
This produces the desired results:
from operator import add, mul
def even_odd(nums):
acc = nums[0] # accumulator
ops = [mul, add]
i = 0
for num in nums[1:]:
acc = ops[i](acc, num)
i = 1 - i # alternates between the two operators
return acc
I am trying to figure out a way to determine the total number of non-matching, common digits between two numbers in python.
So far I can get the number of matching digits between the two numbers.The end goal is to have a function that takes two numbers ie 6621 and 6662 and return the numbers 2 for the number of matching digits and 1 for the number of non-matching shared digits.
I have tried using nested while loops to do this, but the count is not always accurate depending on the numbers being compared.
while i < n:#check 2. Nested while statements
j = 0
while j < n:
if g_list[i] == p_list[j] and j == i:
x
elif g_list[i] == p_list[j]:
z += 1
print(g_list[i],p_list[j],z, i, j)
j += 1
i += 1
You could do it this way:
a = 6661
b = 6662
def find_difference(first, second):
first_list = list(str(first))
second_list = list(str(second))
c = set(first_list)
d = set(second_list)
print((len(c.symmetric_difference(d)),len(c.intersection(d))))
Output:
(2, 1)
You can count the number of occurrence of each digit in each number and take the minimum of those. This will get you the number of common digits, then you subtract the number of matching digits.
def get_count_of_digit(number):
l = [0 for i in range(10)]
list_digit = str(number)
for d in list_digit:
l[int(d)] += 1
return l
def number_of_common_digit(number1, number2):
l1, l2 = [get_count_of_digit(n) for n in (number1, number2)]
return sum([min(l1[i], l2[i]) for i in range(10)])
A Python coding exercise asks to make a function f such that f(k) is the k-th number such that its k-th digit from the left and from the right sums to 10 for all k. For example 5, 19, 28, 37 are the first few numbers in the sequence.
I use this function that explicitly checks if the number 'n' satisfies the property:
def check(n):
#even digit length
if len(str(n)) % 2 == 0:
#looping over positions and checking if sum is 10
for i in range(1,int(len(str(n))/2) + 1):
if int(str(n)[i-1]) + int(str(n)[-i]) != 10:
return False
#odd digit length
else:
#checking middle digit first
if int(str(n)[int(len(str(n))/2)])*2 != 10:
return False
else:
#looping over posotions and checking if sum is 10
for i in range(1,int(len(str(n))/2) + 1):
if int(str(n)[i-1]) + int(str(n)[-i]) != 10:
return False
return True
and then I loop over all numbers to generate the sequence:
for i in range(1, 10**9):
if check(i):
print(i)
However the exercise wants a function f(i) that returns the i-th such number in under 10 seconds. Clearly, mine takes a lot longer because it generates the entire sequence prior to number 'i' to calculate it. Is it possible to make a function that doesn't have to calculate all the prior numbers?
Testing every natural number is a bad method. Only a small fraction of the natural numbers have this property, and the fraction decreases quickly as we get into larger numbers. On my machine, the simple Python program below took over 3 seconds to find the 1,000th number (2,195,198), and over 26 seconds to find the 2,000th number (15,519,559).
# Slow algorithm, only shown for illustration purposes
# '1': '9', '2': '8', etc.
compl = {str(i): str(10-i) for i in range(1, 10)}
def is_good(n):
# Does n have the property
s = str(n)
for i in range((len(s)+1)//2):
if s[i] != compl.get(s[-i-1]):
return False
return True
# How many numbers to find before stopping
ct = 2 * 10**3
n = 5
while True:
if is_good(n):
ct -= 1
if not ct:
print(n)
break
n += 1
Clearly, a much more efficient algorithm is needed.
We can loop over the length of the digit string, and within that, generate numbers with the property in numeric order. Sketch of algorithm in pseudocode:
for length in [1 to open-ended]:
if length is even, middle is '', else '5'
half-len = floor(length / 2)
for left in (all 1) to (all 9), half-len, without any 0 digits:
right = 10's complement of left, reversed
whole-number = left + middle + right
Now, note that the count of numbers for each length is easily computed:
Length First Last Count
1 5 5 1
2 19 91 9
3 159 951 9
4 1199 9911 81
5 11599 99511 81
In general, if left-half has n digits, the count is 9**n.
Thus, we can simply iterate through the digit counts, counting how many solutions exist without having to compute them, until we reach the cohort that contains the desired answer. It should then be relatively simple to compute which number we want, again, without having to iterate through every possibility.
The above sketch should generate some ideas. Code to follow once I’ve written it.
Code:
def find_nth_number(n):
# First, skip cohorts until we reach the one with the answer
digits = 1
while True:
half_len = digits // 2
cohort_size = 9 ** half_len
if cohort_size >= n:
break
n -= cohort_size
digits += 1
# Next, find correct number within cohort
# Convert n to base 9, reversed
base9 = []
# Adjust n so first number is zero
n -= 1
while n:
n, r = divmod(n, 9)
base9.append(r)
# Add zeros to get correct length
base9.extend([0] * (half_len - len(base9)))
# Construct number
left = [i+1 for i in base9[::-1]]
mid = [5] * (digits % 2)
right = [9-i for i in base9]
return ''.join(str(n) for n in left + mid + right)
n = 2 * 10**3
print(find_nth_number(n))
This is a function that exploits the pattern where the number of "valid" numbers between adjacent powers of 10 is a power of 9. This allows us to skip over very many numbers.
def get_starting_point(k):
i = 0
while True:
power = (i + 1) // 2
start = 10 ** i
subtract = 9 ** power
if k >= subtract:
k -= subtract
else:
break
i += 1
return k, start
I combined this with the method you've defined. Supposing we are interested in the 45th number,
this illustrates the search starts at 1000, and we only have to find the 26th "valid" number occurring after 1000. It is guaranteed to be less than 10000. Of course, this bound gets worse and worse at scale, and you would want to employ the techniques suggested by the other community members on this post.
k = 45
new_k, start = get_starting_point(k)
print('new_k: {}'.format(new_k))
print('start at: {}'.format(start))
ctr = 0
for i in range(start, 10**9):
if check(i):
ctr += 1
if ctr == new_k:
break
print(i)
Output:
new_k: 26
start at: 1000
3827
It seems the 45th number is 3827.
In general, a positive natural number that can be multiplied by n
by moving the rightmost digit to the front of the number is called an n
-parasitic number. Here n is itself a single-digit positive natural number. For example: 4×128205=512820
4×128205=512820
so 128205 is a 4-parasitic number. Natural numbers with leading zeros are not allowed. So even though
4×025641=102564
4×025641=102564
the number 025641 is not 4-parasitic.
Assignment: write a function parasitic that takes a natural number. In case the given natural number is n-parasitic, the function must return the value n. Otherwise, the function must return the value 0.
My code (last definition parastic(number)) is not working for some cases for example: parasitic(142857)
n = 5 while with my code I return 0.
def rotateLeft(number):
"""
>>> rotateLeft(717948)
179487
>>> rotateLeft(142857)
428571
>>> rotateLeft(105263157894736842)
52631578947368421
"""
k = str(number)
letter = k[:1]
numb = k[1:]
resultaat = str(numb) + str(letter)
return int(resultaat)
def rotateRight(number):
"""
>>> rotateRight(179487)
717948
>>> rotateRight(428571)
142857
>>> rotateRight(52631578947368421)
15263157894736842
"""
k = str(number)
letter = k[-1]
numb = k[:-1]
resultaat = str(letter) + str(numb)
return int(resultaat)
def parasitic(number):
"""
>>> parasitic(179487)
4
>>> parasitic(142857)
5
>>> parasitic(105263157894736842)
2
>>> parasitic(1234)
0
"""
count = 0
getal = count * number
while getal != rotateLeft(number):
count += 1
getal = count * number
if getal == rotateLeft(number):
break
return (count)
else:
return 0
While using a while loop may improve your grasp of python, this can be solved rather simply using the % operator.
def rotateRight(number):
"""
>>> rotateRight(179487)
717948
>>> rotateRight(428571)
142857
>>> rotateRight(52631578947368421)
15263157894736842
"""
k = str(number)
return int(k[-1] + k[:-1])
def parasitic(number):
rotated = rotateRight(number)
if not rotated % number:
return rotated // number
else:
return 0
This tests to see if number is divisible by the number obtained by a right-rotation, and, if so, returns the divisor (the // operator rounds the result to the nearest integer, but we already know the result must be an integer)
I have written a function that seems to do the job for your examples!
It uses concatenation of string slices and compares this against the num. I think a trick is that n can only ever be between 2 and 11 for this to work as otherwise the shift by 1 at the end would never make the original number.
Here's the code:
def parasitic(num):
for n in range(2, 11):
res = n * num
if str(num)[-1] + str(num)[:-1] == str(res):
return n
return False
Testing:
>>> parasitic(128205)
4
>>> parasitic(142857)
5
>>> parasitic(105263157894736842)
2
>>> parasitic(35)
False
Your issue (having removed break, which is the first issue as it ends before it can return anything):
if getal==rotateLeft(number):
return count
else:
return 0
I think you intended a while-else loop, but you ended up with "if the first result doesn't work, return 0". You need to change indentation so the else lines up the the while (so if no result is found, return 0), not the if. You will also have to add a limit of what to check, or if there is no result it will go on forever.
while getal != rotateLeft(number):
count += 1
getal = count * number
if getal == rotateLeft(number):
return (count)
else:
return 0
If your number is parasitic, the while loop will eventually stop even without you put break in it. I would suggest not to use while loop with this current conditon, since this will be infinity-loop if the number is not parasitic.
But I may show that your code would work if you remove the return in else condition. And also you may want to add both condition of rotateLeft and rotateRight :
def parasitic(number):
count = 0;
getal = count * number;
while getal != rotateLeft(number) and getal != rotateRight(number) :
count += 1
getal = int(count * number)
if getal == rotateLeft(number) or getal == rotateRight(number) :
print(count); print(getal);
return (count)
else:
pass
Hope this helps.
if getal == rotateLeft(number):
break
return (count)
Since break leaves the loop, you cannot ever reach the return statement; your code would simply fall off the end of the function, and return None.
Also, your double-check of getal == rotateLeft(number) signals poor loop design; you should be able to test this once at the top of the loop, without making a second check within.
REPAIR
You have to handle two cases:
If you find a multiplier that matches the rotation, return that multiplier.
If all valid multipliers fail, then you return 0.
So (a) how many multipliers do you try before you give up?
(b) where do you put the two different return statements to handle those cases?
Problem: convert a given decimal number to binary and count the consecutive 1s and display it
Sample Case 1:
The binary representation of 5 is 101, so the maximum number of consecutive 1's is 1.
Sample Case 2:
The binary representation of 13 is 1101 , so the maximum number of consecutive 1's is 2.
Solution:
#!/bin/python3
import sys
n = int(input().strip())
result = []
counter = 1
def get_binary(num):
if num == 1:
result.append(num)
adj(result)
else:
result.append(num%2)
get_binary(int(num/2))
def adj(arr):
global counter
for x in range(0,len(arr)-1):
if arr[x] == 1 and (arr[x] == arr[x+1]):
counter += 1
print(counter)
get_binary(n)
It doesn't pass all the sample test cases. What am I doing wrong?
below is an simplified version that works
def func(num):
return max(map(len, bin(num)[2:].split('0')))
convert integer to binary representation bin(num)
strips 0b from the binary representation bin(num)[:2]
split the string on character 0 bin(num)[2:].split('0')
find the string that has the maximum length and return the number
Here is an alternative solution using regex:
>>> import re
>>> def bn(i):
... n = bin(i)[2:]
... return n,max(len(j) for j in re.findall(r'1+', n))
...
>>>
>>> bn(13)
('1101', 2)
>>> bn(25)
('11001', 2)
Your counter logic is incorrect in a couple of respects, M. Fabre identified the main one. The result is that you count the total quantity of follow-on 1s in all sequences combined, and add 1 from the initial value of counter. rogue-one gave you a lovely Pythonic solution. To repair this at your level of use, go into adj and fix ...
You don't use counter outside the function; keep it local.
Make a second variable that's the best string you've found so far.
Use counter for the current string; when you hit a 0, compare against the best so far, reset counter, and keep going.\
The central logic is something like ...
best = 0
counter = 0
for bit in arr:
if bit == 1:
counter += 1
else:
if counter > best:
best = counter
counter = 0
# After this loop, make one last check, in case you were on the longest
# run of 1s when you hit the end of the bits.
# I'll leave that coding to you.
Some clever answers in here, thought I'd add an alternative using a traditional efficient imperative approach.
This method first converts the number to a string binary representation. From there it updates a stack of longest values, and does a check to see if there is a longer value to be added. Thus you end up with a stack of values that are sorted by longest consecutive 1's. To choose the maximum, simply pop() from the stack.
def longest_consecutive_one(n):
stack = [0]
counter = 0
binary_num = '{0:08b}'.format(n)
length = len(binary_num) - 1
for index, character in enumerate(binary_num):
if character == "1":
counter += 1
if character == '0' or index == length:
if stack[-1] < counter:
stack.append(counter)
counter = 0
return stack.pop()
Sample Output:
>>> longest_consecutive_one(190)
5
>>> longest_consecutive_one(10)
1
>>> longest_consecutive_one(10240)
1
>>> longest_consecutive_one(210231)
6
Output of below written code will give maximum number of consecutive one's in input decimal number.
n = int(raw_input().strip())
num = list((bin(n).split('b'))[1])
num.insert(0,'0')
num.append('0')
count = 0
store = 0
for i in range(0,len(num)):
if ((num[i]) == '1'):
count+=1
elif ('0' == (num[i])) and count !=0:
if count >= store:
store = count
count = 0
print store
this one uses bit magic
def maxConsecutiveOnes(x):
# Initialize result
count = 0
# Count the number of iterations to
# reach x = 0.
while (x!=0):
# This operation reduces length
# of every sequence of 1s by one.
x = (x & (x << 1))
count=count+1
return count
# Driver code
print(maxConsecutiveOnes(14))
print(maxConsecutiveOnes(222))
the output will be 3 and 4
#include<bits/stdc++.h>
using namespace std;
int main()
{
int n;
int count=0,min=0;
cin>>n;
for(int i=0;n>0;i++)
{
if(n%2==1)
{
count++;
if(count>min)
{
min=count;
}
}
else
{
count=0;
}
n = n/2;
}
cout<<min<<endl;
return 0;
}
I think the 1st answer is the best. I had done it in a similar manner and might be easier to understand.
import sys
if __name__ == '__main__':
n = int(input())
bina=str(format(n,'b'))
holder=bina.split('0')
max_num = max(holder,key=len)
print(len(max_num))
You can solve this problem using Loop and List, as shown below:
def maxConsecutive(n):
binary = format(n,'b')
print(f"The Binary Represntation of the number {n} is = {binary}")
length = len(binary)
count =0 #Create a Counter Variable to Count the Number of 1's
#Create a blank Array to store the values of number of Consecutive 1's:
Store = []
for i in range(length):
#Check if the number is 1,if yes increase the value of counter variable
if (binary[i]=='1'):
count+=1
#Check if the number is 0 or last digit of the binary number:
#to store the value of counter in the list and set the counter variable to 0
if (binary[i]=='0' or i == length-1):
if (count!=0): #To not add count=0 in the List
Store.append(count)
count = 0
print("The List of Number of Consecutive 1's is : ",Store)
print("The Maximum Number of consecutive 1 is: ",max(Store))
#Driver Code:
n = int(input("Enter the Number: "))
maxConsecutive(n)