Python Lists.What am I missing? - python

from random import *
def f(one):
x=randrange(0,len(one))
y=randrange(0,len(one))
return(one)
print(one(["20","40","60"]))
the function is supposed to take an input parameter a list of strings and generates two random numbers between 0 and the length of the list but how do you return the list with the slice between the two numbers removed.

First you are not calling the function you've created, you must:
print( f(["20","40","60"]) )
Second, your function f() is not doing anything, is just creating two variables x and y but returning the same list it received as parameter.
And to return the sliced list:
from random import *
def f(one):
x=randrange(0,len(one))
y=randrange(0,len(one))
print (x, y)
return one[x:y]
print(f(["20","40","60"]))
Remember that randrange(x, y) returns a value between x and y - 1

The sublist of a list one from index i up to (but not including!) index j is written in Python as one[i:j]. I think you can figure out the rest from here.

Related

Implementing fuction that takes in array and multiplies each element by given int [duplicate]

This question already has answers here:
Trying to modify a list in Python
(3 answers)
Closed 4 years ago.
def multAll(A, k):
# takes an array of integers and an int, and multiplies each integer by the int.
for i in A:
i = i*k
return i
# test 1
A = [5,12,31,7,25]
multAll(A, 10)
print(A) # should print [50,120,310,70,250]
What am I doing wrong in multAll that isnt giving me the correct answer?
When return i happens for the first time in your function, the function stops and returns the current i.
def multAll(A, k):
return_value = []
for i in A:
i = i*k
return_value.append(i)
return return_value
Like this, a complete list return_value is created, and that list is returned.
This will give you the desired result:
def multAll(A, k):
return [i * k for i in A]
It is using the list comprehension pattern that allows you to edit each element of the list.
As written, your function should not return the given list; it should return the value of A[0] * k, the scalar 50.
Let's walk through the code for a moment, as you should have done with a print statement before posting.
for i in A:
# i is a local variable; it takes on the value of A[0], or 5
i = i*k
# i is now 50
return i
# You return 50 to the calling program -- which ignores the return value.
At this point, the function is done, gone, exited, and will execute no more until you call it again.
To get the list (you have a list, not an **array*) altered, you can change each element in place. Don't leave the function until you've processed all of the elements.
for i in range(len(A)):
A[i] *= k
return
Since you're calling the multAll function without expecting a returning value, you should update the list A in-place by updating its item values through indices:
def multAll(A, k):
for i in range(len(A)):
A[i] *= k
Numbers are not the objects, so In loop every time you get only the next value of a list. And to that value, you do that operation. You should iterate over indexes, and assign a value to a specific place in the list. You could use the range function to do that.
Another problem is that you return value after calculating the first value in the list, so you should remove one indention.

How to get minimum odd number using functions from list

I'm trying to get the minimum odd number using python. I used lambda, loops and other methods to get minimum odd number but i was not able to get that using functions. here is my code
z= [1,8,-4,-9]
def min_odd(x):
for i in x:
if (i%2!=0):
return min(i)
y = min_odd(z)
print (y)
Can some please tell me what i was missing here.
The min() function expects an iterable like a list which it will then yield the smallest element from.
E.g. min([1,0,3]) gives 0.
So if you want to use it, you must create a list (or other iterable) of the odd numbers that you can then pass into it:
def min_odd(x):
odds = []
for i in x:
if i % 2 != 0:
odds.append(i)
return min(odds)
note that we could also use a list-comprehension:
def min_odd(x):
return min([i for i in x if i % 2 != 0])
which both work.
An alternative method would be to store the current minimum odd value in a variable and update this variable if we come across a smaller odd value:
def min_odd(x):
min_v = float('inf')
for i in x:
if i % 2 != 0 and i < min_v:
min_v = i
return min_v
Try:
min([val for val in z if val % 2 != 0])
It seems your code logics are wrong. First off, you seem to have an indentation error in the return statement. Second off, the min() function requires a collection of items (like an array for example) or a series of arguments to determine the minimum in that series. You can try multiple things.
Use another variable to store a temporary minimum. Replace it every time you find a smaller odd value ( for every i in x... if the value is odd and is smaller than the previous odd value, replace it) and have it started with the first odd number you can find.
Take all the odd numbers and add them to another array on which you will apply the min function.
Hope this proves useful!
You could pass a generator into the min() function:
def min_odd(iterable):
return min(i for i in iterable if i % 2)
I didn't write i % 2 != 0 because any odd number will return 1 which has a Boolean value of True.
I added a parameter to the function that takes the iterable so it can be used for any iterable passed in.
min operates on an iterable. i is not an iterable in your code; it's the last element of the list.
You can achieve what you want with a filter, though:
min(filter(lambda e: e%2 != 0, x))

TypeError: unsupported operand type(s) for ** or pow(): 'list' and 'int'

I'm trying to take the values from the previous function and use in another function. This is my first programming class and language, and i'm totally lost.
I figured out how to take the variables from astlist and put them into the function distance, but now Python is telling me I can't use these variables in an equation because they're in a list now? Is that what it's saying?
I'm also just printing the lists to see if they are running. These are two of my functions, and the functions are both defined in my main function.
I'm taking these lists and eventually putting them into files, but I need to figure out why the equation isn't working first. Thanks!
def readast():
astlist = []
for j in range(15):
list1 = []
for i in range(3):
x = random.randint(1,1000)
y = random.randint(1,1000)
z = random.randint(1,1000)
list1.append([x,y,z])
astlist.append(list1)
print(astlist)
return astlist
def distance(astlist):
distlist = []
for row in range(len(astlist)):
x, y, z = astlist[row]
x1 = x**2
y2 = y**2
z2 = z**2
equation = math.sqrt(x+y+z)
distlist.append(equation)
print(distlist)
return distlist
The variable astlist is a list. You're adding list1 to it several times which is also a list. But you're also adding a list to list1 each time: list1.append([x,y,z]). So ultimately astlist is a list containing multiple lists which each contain a list with three integers.
So when you write x,y,z=astlist[row] the variables x, y and z are actually lists, not integers. This means you're trying to compute x**2 but x is a list, not a number. This is why Python is giving you an error message as ** doesn't support raising a list to a power.
I'm not sure what you're trying to accomplish with all these lists but you should change the code so that you're only trying to raise numbers to the power of two and not lists.
There are a few problems here:
Firstly the loop at the top of readast() sets list1 to [] 15 times - I'm not sure what you're trying to do here. If you are trying to generate 15 sets of x,y,z coordinates then it is the second range - in your example the range(3)
- that you need to change.
Then you keep adding lists of [x,y,z] to (the same) list1, then adding the whole of list1 to astlist. However, Python actually stores a pointer to the list rather than a copy so when you add items to list1, it adds items to list1 whereever list1 is included in another list:
In this example the random numbers are replaced with sequential numbers for clarity (the first random number is 1, the second 2 and so on):
After first cycle of loop:
list1: [[1,2,3]]
astlist: [[[1,2,3]]]
After second cycle of loop:
list1: [[1,2,3],[4,5,6]]
astlist: [[[1,2,3],[4,5,6]],[[1,2,3],[4,5,6]]]
and so on
As you can see, list1 is now a list of lists, and astlist is now a list of duplicates of list1 (a list of lists of lists)
list1 is probably redundant and you probably want just
astlist.append([x,y,z])
in the first bit.
In the second function, you use
for row in range(len(astlist)):
x,y,z=astlist[row]
...
but actually the following would be better:
for row in astlist:
x,y,z=row
...
or even:
for x,y,z in astlist:
...
as for loops in Python iterate over members of a sequence (or other iterable value) rather being just a simple counter. What you are doing with the range(len(astlist)) construct is actually generating a list [1,2,3...] and iterating over that.
If you particularly need a numerical index then you can use the enumerate function which returns a series of (index,value) pairs that you can iterate over thus:
for i,value in enumerate(['apple','banana','cherry']):
print 'value {} is {}'.format(i,value)
value 0 is apple
value 1 is ball
value 2 is cherry
Hope this helps
I will refer to the specific type error (TypeError: unsupported operand type(s) for ** or pow(): 'list' and 'int'), for some reason arrays are iterable objects for operations like addition: sum(array), but, power: array**2, pow(array,2). You can solve this with some extra steps as follow:
x1 = [j**2 for j in x]
also I recommend to use sum function
sum(x,y,z)
remember all this is to avoid the error message that you were referring to
that way you apply the power of 2 to each element in the array, getting a new array and avoiding the error message that you were asking help for. It seems to me that you are looking to get a normalization of your data using norm L2, if that is true, well, I think you are missing half of it.

how to zip function with two arrays as a return value - Python

how do I create tuple from two randomly generated lists with separate function ? zip function will create only tuple of those two arrays as whole but I need the numbers to be coupled like (1,2),(3,4). Thanks.
import random
def ars():
arr1 = []
arr2 = []
for i in range(10):
x = random.randrange(100)
arr1.append(x)
for j in range(10):
y = random.randrange(100)
arr2.append(y)
return(arr1,arr2)
x = ars()
print x
y = zip(ars())
print y
zip function accepts multiple iterables as its arguments, so you simply have to unpack the values from the returned tuple with * (splat operator):
y = zip(*ars())
With zip(([1], [2])) only one iterable is submitted (that tuple).
In zip(*([1], [2])) you unpack 2 lists from tuple, so zip receives 2 iterables.
You can avoid having to zip by using map
def ars(arr_len, rand_max):
return [map(random.randrange, [rand_max]*2) for x in range(arr_len)]
call ars like: ars(10,100), if you really need tuples instead of lists, wrap the map statement in a tuple() function.

replacing .join() using python

I am learning python and was going through my tutorial. I came across this code segment and want to know if it can be replaced using a simple loop without using inbuilt .join()
return choice("".join(x * y for x, y in items))
Can someone help me with this?
You can:
value = ''
for x, y in items:
value += x * y
return choice(value)
but know that this will be slower as you now have to build a new string value for each and every iteration over items. The ''.join() only has to build one new string object.
If choice() is random.choice(), x is a string and y an integer, and this is a weighted random choice function, you should also be able to use a list:
value = []
for x, y in items:
value += list(x) * y
return choice(value)

Categories

Resources