Python implementation of set relations - python

How would I implement the following using python? I've tried using lambda expressions and a few other methods, but I'm not getting the desired results. Basically, I should receive a set of relations that satisfy the check. I.E they have to be divisible by each other, so {(1,1), (1,2), (1,3),...(6,6)}.
Here's the actual question:
In Python, set a variable say S = {1,2,3,4,5,6}; then do as follows: "List all the ordered pairs in the relation R = {(a,b) : a divides b} on the set {1,2,3,4,5,6}."

you can do it by list comprehension -
S = [1,2,3,4,5,6]
result = [ (x,y) for x in S for y in S if y%x==0]

You can use itertools.product within a list comprehension,and as you want they be divisible by each other you can use the condition i%j==0 or j%i==0 :
>>> from itertools import product
>>> [(i,j) for i,j in product(S,repeat=2) if i%j==0 or j%i==0]
[(1, 1), (1, 2), (1, 3), (1, 4), (1, 5), (1, 6), (2, 1), (2, 2), (2, 4), (2, 6), (3, 1), (3, 3), (3, 6), (4, 1), (4, 2), (4, 4), (5, 1), (5, 5), (6, 1), (6, 2), (6, 3), (6, 6)]

[{(a,b) : a/b} for a in S for b in S]

Related

Numpy: reshape list of tuples

I have the following list of tuples:
>>> import itertools
>>> import numpy as np
>>> grid = list(itertools.product((1,2,3),repeat=2))
>>> grid
[(1, 1), (1, 2), (1, 3), (2, 1), (2, 2), (2, 3), (3, 1), (3, 2), (3, 3)]
I'd like to reshape this list in a sensible way (e.g. using numpy if possible) to be 3x3 as follows:
[[(1, 1), (1, 2), (1, 3)],
[(2, 1), (2, 2), (2, 3)],
[(3, 1), (3, 2), (3, 3)]]
When I do np.reshape(grid, (3, 3)) I get the following error: ValueError: cannot reshape array of size 18 into shape (3,3) (size 18??)
I've tried variations of np.reshape(grid, (3, 3, 2)) but these don't return the 3x3 grid given above.
This will do the job:
new_grid = np.empty(len(grid), dtype='object')
new_grid[:] = grid
new_grid = new_grid.reshape(3, 3)
This outputs:
array([[(1, 1), (1, 2), (1, 3)],
[(2, 1), (2, 2), (2, 3)],
[(3, 1), (3, 2), (3, 3)]], dtype=object)
The object type will remain tuple:
type(new_grid[0, 0])
tuple
18 comes from the fact that you have a list of 9 tuples, each containing 2 items; thus, 9 * 2 = 18. numpy automatically converts the tuples to part of the array.
You can either use LeonardoVaz's answer or do it speedily with nested list comprehension:
reshaped_grid = [[grid[i+j] for j in range(3)] for i in range(0, len(grid), 3)]
Output:
>>> reshaped_grid
[
[(1, 1), (1, 2), (1, 3)],
[(2, 1), (2, 2), (2, 3)],
[(3, 1), (3, 2), (3, 3)]
]

Reduce to combination of list in items of tuples

I have list of tuples, I want to learn new one and I wonder how to elegantly sort out items from this list of tuples and remove all duplicates, as if duplicates (6, 1) and (1, 6) would be equal to each other. I so I'd need minimum combination.
lst = [(1, 1), (4, 1), (1, 4), (3, 1), (1, 3), (9, 1), (1, 9), (6, 1), (1, 6), (5, 1), (1, 5)]
I have tried:
res = set([tuple(sorted(list(x))) for x in lst])
And it works, but is some kind of spaghetti programming. Is there more elegant way?
There are no "elegant" ways at times ... but the example below, reproduces the same result, but using lambda.
set(map(lambda element: tuple(sorted(element)), lst))
{(1, 3), (1, 4), (1, 5), (1, 6), (1, 9), (1, 1)}

Product of coordinates with specific order of iteration

Here's a snippet with a regular itertools.product usage:
from itertools import product
arr = [1,2,3]
pairs = list(product(arr, arr))
# pairs = [(1, 1), (1, 2), (1, 3), (2, 1), (2, 2), (2, 3), (3, 1), (3, 2), (3, 3)]
Now I would like to have these points yielded in an order which can be achieved by sorting the resulting tuples in the following way:
sorted(pairs, key=lambda y:max(y))
# [(1, 1), (1, 2), (2, 1), (2, 2), (1, 3), (2, 3), (3, 1), (3, 2), (3, 3)]
Is there a way for me to input those numbers to itertools.product so it yields the tuples in this order, or do I need to sort the pairs after iterating over the results of itertools.product?
You can probably use your own modified approach to achieve this in one go.
sorted([(x, y) for x in [1, 2, 3] for y in [1, 2, 3]], key=lambda y:max(y))
OUTPUT
[(1, 1), (1, 2), (2, 1), (2, 2), (1, 3), (2, 3), (3, 1), (3, 2), (3, 3)]

Find max value of tuple with multiple values being the same

I have a list of tuples, and I need to find the tuple with the max value on the right side. I also need the program to print out each tuple that has this max value. I have tried using lambda, but that only returns one of the tuples with a max value on the left side. Specifically, I have tried:
max(TotalFriendsList,key=lambda x:x[1])
Which returns (1,3)
This is the list:
[(0, 2),
(1, 3),
(2, 3),
(3, 3),
(4, 2),
(5, 3),
(6, 2),
(7, 2),
(8, 3),
(9, 1)]
This is the output i need:
[(1,3),
(2,3),
(3,3),
(5,3),
(8,3)]
Thanks!
You can keep this fairly compact by getting the highest value, then getting corresponding tuples:
l = [(0, 2),
(1, 3),
(2, 3),
(3, 3),
(4, 2),
(5, 3),
(6, 2),
(7, 2),
(8, 3),
(9, 1)]
# pass a generator expression to `max`
greatest = max(item[1] for item in l)
# "filter" `l`, keeping only tuples that have the greatest value as their second element
result = [item for item in l if item[1] == greatest]
print(result)
# [(1, 3), (2, 3), (3, 3), (5, 3), (8, 3)]
>>> lst = [(0, 2),
... (1, 3),
... (2, 3),
... (3, 3),
... (4, 2),
... (5, 3),
... (6, 2),
... (7, 2),
... (8, 3),
... (9, 1)]
>>> mx = max(lst, key=lambda x: x[1])
>>> filter(lambda x: x[1] == mx[1], lst)
[(1, 3), (2, 3), (3, 3), (5, 3), (8, 3)]
This now, after optimization, goes through the list exactly once:
data = [(0, 2),
(1, 3),
(2, 3),
(3, 3),
(4, 2),
(5, 3),
(6, 2),
(7, 2),
(8, 3),
(9, 1)]
maxVal = -1
result = None
for datum in data:
val = datum[1]
if val > maxVal:
result = [datum]
maxVal = val
elif val == maxVal:
result.append(datum)
print result
print
# and the way he wanted it printed...
print "[" + ",\n".join([str(v) for v in result]) + "]"
Notice that since the first entry contains a "winning tuple", this code doesn't process the losers at all. It just does a few comparisons for them, and comparisons cost almost nothing. So it basically does the bare minimum amount of work of building the result list in a single pass. It wouldn't be so efficient if the first tuple weren't a winner.
Output:
[(1, 3), (2, 3), (3, 3), (5, 3), (8, 3)]
[(1, 3),
(2, 3),
(3, 3),
(5, 3),
(8, 3)]
Only I did just what the guy asked for ;) (tic) - all answers were right on...good perpective on different ways to do the same problem

how to print max size of list inside a list

For example:
alist=[[(0, 0), (0, 1), (1, 1), (1, 2), (2, 2), (2, 1), (2, 0), (1, 0), (3, 0)],
[(0, 2), (0, 3), (1, 3)],
[(0, 4), (1, 4), (2, 4), (0, 5), (0, 6), (1, 6), (2, 6), (3, 6)],
[(1, 5)],
[(2, 3), (3, 3), (3, 4), (3, 5), (2, 5), (3, 2), (3, 1)]]
for i in dlist:
print(len(i))
print(max(len(i))) #this gives me error
output:
5
9
3
8
1
7
I wanted to print out 9 as my output from the above list. How am I able to print the result?
Somewhat more terse
len(max(alist,key=len))
If you can be sure your nesting is only one level (that is, a list of lists):
print max(len(sublist) for sublist in alist)
functional style using map:
print max(map(len, alist))
If you want the actual index of the longest sublist:
max(((i,l) for i,l in enumerate(alist)), key=lambda t: len(t[1]))[0]
Or, as stated in comments:
max(enumerate(alist), key=lambda t: len(t[1]))[0]

Categories

Resources