How to take Different multi line inputs? - python

The other day, for the first time I participated in a coding contest and I faced an issue with taking inputs. There were 4 sample cases and each sample case had n test cases. So each sample case was in the format:
First line denotes number of test cases
Second line denotes number of elements in array A
Third line denotes elements of array A
Fourth line denotes elements of array B
To make more sense, the input was (say),
3 // Number of test cases
5 // Size of array A
2 4 3 7 9 // array A
14 21 11 // array B
3 // Size of array A
6 7 2 // array A
9 8 // array B
4 // Size of array A
5 2 6 7 // array A
12 17 // array B
The solution that I tried was
t = int(input()) # Number of sample cases
for i in t:
n = int(input()) # Size of array A
arr_A = [int(x) for x in input().split()]
arr_B = [int(x) for x in input().split()]
# Statements...
When I was running the code I was getting EOF error or some error. To test what was causing the error I reduced the aforementioned sample case to
1 // Number of test cases
5 // Size of array A
2 4 3 7 9 // array A
14 21 11 // array B
And with this input the code was running fine.
I will truly appreciate if you tell me possible ways of taking such inputs?

In your code, for i in t should be modified to for i in range(t) since we need to iterate up to a certain number.
This is the approach I usually use when it comes to taking inputs.
t = int(input())
while t > 0:
n = int(input())
arrA = list(map(int, input().split()))
arrB = list(map(int, input().split()))
t-=1

Related

How to use a loop in python to return elements of an array into a given set?

For each index of a sorted array i = 1,...,N in this new array I want to find all indexes j such that xj is in the set (xi-5, xi+5).
x= np.array([1,2,2,3,4,6,7,9])
n=len(x)
for i in range(n):
for j in range(n):
if x[i] - 5 < x[j] and x[i] + 5 > x[j]:
print(j)
So for this array example I gave, when i=0, x=1. So it should return [1,2,3,4] because they are all in (x_1-5, x_1+5). Then when i=1, x=2, and should return [0,2,3,4,5] and so on. I should get N arrays.
But, the output gives me
0 1 2 3 4 0 1 2 3 4 5 0 1 2 3 4 5 0 1 2 3 4 5 6 0 1 2 3 4 5 6 1 2 3 4 5 6 7 3 4 5 6 7 5 6 7
I don't know how I can implement this and I think the problem is for j in x since it is the same as the first loop. In my eyes, it says for every i, if any xj is in (xi-5,xi+5) then return the jth element. But, I want to return N sets.
Writing your indexes that way is probably what is confusing you.
If you want to access an index that is n-2 then you have to index it that way.
What you are doing is accessing the nth index of your list and then subtracting or adding 2 from the value that you accessed.
x[i]
returns whatever value is at position i in the list.
x[i-2]
will return whatever value is at position i-2.
Also you will need to account for the fact that subtracting any number from your index variable will cause your resulting index to be out of bounds if the resulting index is greater than the length of the list - 1 or less than 0.
If you are looking for duplicates the best way is to sort first then compare neighbors.
for i in x:
if x[i] == x[i+1]:
print i;
Subsetting is done like this: x[i-2:i+2]
So to divide into n sets of 2 elements you would:
n=2
for i in x:
if i+n < len(x):
return x[i:i+n];
To divide into n sets of equal number of elements you would:
n = // Some arbitrary number.
j = int(len(x) / n);
for i in x:
if i+j < len(x):
return x[i:i+j];

Sorting a random array using permutation

I tried to sort an array by permuting it with itself
(the array contain all the numbers in range between 0 to its length-1)
so to test it I used random.shuffle but it had some unexpected results
a = np.array(range(10))
random.shuffle(a)
a = a[a]
a = a[a]
print(a)
# not a sorted array
# [9 5 2 3 1 7 6 8 0 4]
a = np.array([2,1,4,7,6,5,0,3,8,9])
a = a[a]
a = a[a]
print(a)
# [0 1 2 3 4 5 6 7 8 9]
so for some reason the permutation when using the second example of an unsorted array returns the sorted array as expected but the shuffled array doesn't work the same way.
Does anyone know why? Or if there is an easier way to sort using permutation or something similar it would be great.
TL;DR
There is no reason to expect a = a[a] to sort the array. In most cases it won't. In case of a coincidence it might.
What is the operation c = b[a]? or Applying a permutation
When you use an array a obtained by shuffling range(n) as a mask for an array b of same size n, you are applying a permutation, in the mathematical sense, to the elements of b. For instance:
a = [2,0,1]
b = np.array(['Alice','Bob','Charlie'])
print(b[a])
# ['Charlie' 'Alice' 'Bob']
In this example, array a represents the permutation (2 0 1), which is a cycle of length 3. Since the length of the cycle is 3, if you apply it three times, you will end up where you started:
a = [2,0,1]
b = np.array(['Alice','Bob','Charlie'])
c = b
for i in range(3):
c = c[a]
print(c)
# ['Charlie' 'Alice' 'Bob']
# ['Bob' 'Charlie' 'Alice']
# ['Alice' 'Bob' 'Charlie']
Note that I used strings for the elements of b ton avoid confusing them with indices. Of course, I could have used numbers from range(n):
a = [2,0,1]
b = np.array([0,1,2])
c = b
for i in range(3):
c = c[a]
print(c)
# [2 0 1]
# [1 2 0]
# [0 1 2]
You might see an interesting, but unsurprising fact: The first line is equal to a; in other words, the first result of applying a to b is equal to a itself. This is because b was initialised to [0 1 2], which represent the identity permutation id; thus, the permutations that we find by repeatedly applying a to b are:
id == a^0
a
a^2
a^3 == id
Can we always go back where we started? or The rank of a permutation
It is a well-known result of algebra that if you apply the same permutation again and again, you will eventually end up on the identity permutation. In algebraic notations: for every permutation a, there exists an integer k such that a^k == id.
Can we guess the value of k?
The minimum value of k is called the rank of a permutation.
If a is a cycle, then the minimum possible k is the length of the cycle. In our previous example, a was a cycle of length 3, so it took three applications of a before we found the identity permutation again.
How about a cycle of length 2? A cycle of length 2 is just "swapping two elements". For instance, swapping elements 0 and 1:
a = [1,0,2]
b = np.array([0,1,2])
c = b
for i in range(2):
c = c[a]
print(c)
# [1 0 2]
# [0 1 2]
We swap 0 and 1, then we swap them back.
How about two disjoint cycles? Let's try a cycle of length 3 on the first three elements, simultaneously with swapping the last two elements:
a = [2,0,1,3,4,5,7,6]
b = np.array([0,1,2,3,4,5,6,7])
c = b
for i in range(6):
c = c[a]
print(c)
# [2 0 1 3 4 5 7 6]
# [1 2 0 3 4 5 6 7]
# [0 1 2 3 4 5 7 6]
# [2 0 1 3 4 5 6 7]
# [1 2 0 3 4 5 7 6]
# [0 1 2 3 4 5 6 7]
As you can see by carefully examining the intermediary results, there is a period of length 3 on the first three elements, and a period of length 2 on the last two elements. The overall period is the least common multiple of the two periods, which is 6.
What is k in general? A well-known theorem of algebra states: every permutation can be written as a product of disjoint cycles. The rank of a cycle is the length of the cycle. The rank of a product of disjoint cycles is the least common multiple of the ranks of cycles.
A coincidence in your code: sorting [2,1,4,7,6,5,0,3,8,9]
Let us go back to your python code.
a = np.array([2,1,4,7,6,5,0,3,8,9])
a = a[a]
a = a[a]
print(a)
# [0 1 2 3 4 5 6 7 8 9]
How many times did you apply permutation a? Note that because of the assignment a =, array a changed between the first and the second lines a = a[a]. Let us dissipate some confusion by using a different variable name for every different value. Your code is equivalent to:
a = np.array([2,1,4,7,6,5,0,3,8,9])
a2 = a[a]
a4 = a2[a2]
print(a4)
Or equivalently:
a = np.array([2,1,4,7,6,5,0,3,8,9])
a4 = (a[a])[a[a]]
This last line looks a little bit complicated. However, a cool result of algebra is that composition of permutations is associative. You already knew that addition and multiplication were associative: x+(y+z) == (x+y)+z and x(yz) == (xy)z. Well, it turns out that composition of permutations is associative as well! Using numpy's masks, this means that:
a[b[c]] == (a[b])[c]
Thus your python code is equivalent to:
a = np.array([2,1,4,7,6,5,0,3,8,9])
a4 = ((a[a])[a])[a]
print(a4)
Or without the unneeded parentheses:
a = np.array([2,1,4,7,6,5,0,3,8,9])
a4 = a[a][a][a]
print(a4)
Since a4 is the identity permutation, this tells us that the rank of a divides 4. Thus the rank of a is 1, 2 or 4. This tells us that a can be written as a product of swaps and length-4 cycles. The only permutation of rank 1 is the identity itself. Permutations of rank 2 are products of disjoint swaps, and we can see that this is not the case of a. Thus the rank of a must be exactly 4.
You can find the cycles by choosing an element, and following its orbit: what values is that element successively transformed into? Here we see that:
0 is transformed into 2; 2 is transformed into 4; 4 is transformed into 6; 6 is transformed into 0;
1 remains untouched;
3 becomes 7; 7 becomes 3;
5 is untouched; 8 and 9 are untouched.
Conclusion: Your numpy array represents the permutation (0 -> 2 -> 4 -> 6 -> 0)(3 <-> 7), and its rank is the least common multiple of 4 and 2, lcm(4,2) == 4.
it's took some time but I figure a way to do it.
numpy doesn't have this fiture but panda does have.
by using df.reindex I can sort a data frame by it indexes
import pandas as pd
import numpy as np
train_df = pd.DataFrame(range(10))
train_df = train_df.reindex(np.random.permutation(train_df.index))
print(train_df) # random dataframe contaning all values up to 9
train_df = train_df.reindex(range(10))
print(train_df) # sort data frame

Kickstart Round C 2020 Countdown Problem - finding number of contiguous subarray

Edit - The output didn't have a space before the colon. But after changing that, instead of wrong answer, it's saying runtime error. Even the sample input tests ran successfully. What could possible be wrong?
Problem
Avery has an array of N positive integers. The i-th integer of the array is Ai.
A contiguous subarray is an m-countdown if it is of length m and contains the integers m, m-1, m-2, ..., 2, 1 in that order. For example, [3, 2, 1] is a 3-countdown.
Can you help Avery count the number of K-countdowns in her array?
Input
The first line of the input gives the number of test cases, T. T test cases follow. Each test case begins with a line containing the integers N and K. The second line contains N integers. The i-th integer is Ai.
Output
For each test case, output one line containing Case #x: y, where x is the test case number (starting from 1) and y is the number of K-countdowns in her array.
Limits
Time limit: 20 seconds per test set.
Memory limit: 1GB.
1 ≤ T ≤ 100.
2 ≤ K ≤ N.
1 ≤ Ai ≤ 2 × 105, for all i.
Test set 1
2 ≤ N ≤ 1000.
Test set 2
2 ≤ N ≤ 2 × 105 for at most 10 test cases.
For the remaining cases, 2 ≤ N ≤ 1000.
Sample
Input
3
12 3
1 2 3 7 9 3 2 1 8 3 2 1
4 2
101 100 99 98
9 6
100 7 6 5 4 3 2 1 100
Output
Case #1: 2
Case #2: 0
Case #3: 1
T = int(input())
res = []
for i in range(T):
N, K = map(int, input().split(' '))
ai = list(map(int, input().split(' ')))
y=0
count=0
for m in range(len(ai)):
count=0
if(ai[m]==K):
if(len(ai)>=m+K-1):
for j in reversed(range(1, K)):
if(ai[m+K-j]==j):
count=count+1
if(count==K-1):
y=y+1
else:
break
else:
continue
res.append("Case #"+str(i+1)+" : "+str(y))
for g in range(len(res)):
print(res[g])
You can use a two-pointer approach like take two variables i and j and initialize both with 0
Keeping i fixed increment j if the required condition is met i.e.
while(a[k+1]-a[k]==1):
j++
k++
wherever condition fails, calculate j-i. If at all j-i==m then increment your counter say cnt and then put i=j and repeat until the end of array

Read k matrices size nxm from stdin in Python

I need to read k matrices size nxm from stdin in Python.
In the first line there must be the number of matrices (k), and then - k descriptions of matrices: in the first line 2 integer numbers for size (n and m) devided by space, then the matrix.
Here's an example:
2
2 3
4 5 6
3 1 7
4 4
5 3 4 5
6 5 1 4
3 9 1 4
8 5 4 3
Could you please tell me how I can do this?
I could have done this only without considering m (for 1 matrix):
n = int(input())
a = []
for i in range(n):
a.append([int(j) for j in input().split()])
I have found some similar questions but stdin is not used (e.g. reading from file is used) or the size of string in matrix is not set.
You are on a right way. try to break it in simple steps. Basically a n X m matrix is n rows and each row would have m elements (pretty obvious). what if we have n=1 then we have a line in which there would be m element. to take such input we would just
matrix = input().split() #read the input
matrix = [ int(j) for j in matrix] #matrix is now 1 x m list
or simplify this
matrix = [ int(j) for j in input().split() ]
now suppose we have n rows, that means we have to do this n times which is simply looping n times ,
matrix = [ [ int(j) for j in input().split() ] for i in n ]
a more pythonic way is using map,
matrix= [ list( map(int, input().split() ) ) for i in range(n) ]

Extracting indices from numpy array python

I want the last 4 values of this equation.
Is there a better way to this in one step, like modifying the equation or another extraction technique other than using delete
a=5
d=2
n = np.cumsum(d ** np.arange(1, a+1))
print 'n=', n
n = np.delete(n,0)
print 'n extracted=', n
n= [ 2 6 14 30 62]
n extracted= [ 6 14 30 62]
print n[-4::]
will print the last 4 elements. You can do all kinds of array slicing like this, the above was just an example. You can index the array from the front or the back.

Categories