Get x1,x2 provided that x belongs to [x1,x2] - python

Given:
xvalues = [0.0, 1829.0, 3658.0, 5487.0]
and
nodesF = [[1, 0, 0, 0], [2, 0.5, 0, 0], [3, 5487, 0, 0]]
I want to loop over nodesF and return x1 and x2 values which every x of nodesF lie between, i.e. x belongs to [x1,x2] with x1<x2.
My code is:
for nodeID, x, y, z in nodesF:
x2= min(value for value in xvalues if value >= x)
x1= max(value for value in xvalues if value <= x)
if x1==x2:
x1=None
x2=None
x2= min(value for value in xvalues if value > x)
x1= max(value for value in xvalues if value <= x)
if x2==None or x2<=x1:
x2= min(value for value in xvalues if value >= x)
x1= max(value for value in xvalues if value < x)
elif x1==None or x2<=x1:
print "Error"
For x=5487 I get:
x2= min(value for value in xvalues if value > x) ValueError: min() arg
is an empty sequence.
So my question is how do get pass this error? if I could just set x2=None when min() is empty it would be OK! Thanks!

You're on the right track, but you'll need to do the check the list yourself:
valid_values = [value for value in xvalues if value > x] #changed >= by >
if valid_values:
x2 = min(valid_values)
else:
x2 = None
Or you could catch the error after the fact:
try:
x2 = min(value for value in xvalues if value > x) #changed >= by >
except ValueError:
x2 = None

So two lines might seem a little terse, but I hope you like it:
r = zip([float('-inf')] + xvalues, xvalues + [float('inf')])
which produces this:
In [104]: print r
Out[104]: [(-inf, 0.0), (0.0, 1829.0), (1829.0, 3658.0), (3658.0, 5487.0), (5487.0, inf)]
Then get your ranges like this:
[[filter(lambda l: l[0] < n <= l[1], r)[0] for n in m] for m in nodesF]
which produces this:
Out[102]:
[[(0.0, 1829.0), (-inf, 0.0), (-inf, 0.0), (-inf, 0.0)],
[(0.0, 1829.0), (0.0, 1829.0), (-inf, 0.0), (-inf, 0.0)],
[(0.0, 1829.0), (3658.0, 5487.0), (-inf, 0.0), (-inf, 0.0)]]

Related

How to restrict the contour plot only to 3sigma variation for a 2Dimensional gaussian?

I was a bit curious on plotting the contour plots for a 2 dimensional gaussian distribution. In my case, for a given set of 2D points, I cluster them into different grid cells and compute the covariance matrix for every cell and plot the gaussian distribution for each and every cell. When I plot I do not want the entire contour for the cell but the distribution restricted within 3 sigma of the data points. Is there anyway it could be done ?
My code is as follows:
import numpy as np
import matplotlib.pyplot as plt
def createCells():
partition = 4
coords = [np.linspace(-1.0 , 1.0, num = partition + 1) for i in range(2)]
x, y = np.meshgrid(*coords)
return x, y
def probab(mean, covMat, lPoints):
lPoints = lPoints[..., np.newaxis] if lPoints.ndim == 2 else lPoints ## Create vectorized values for the x, y
if np.linalg.det(covMat) > 0:
factor1 = (2*np.pi)*(np.linalg.det(covMat)**(-1/2))
factor2 = np.exp((-1/2)*np.einsum('ijk,jl,ilk->ik', lPoints - mean, np.linalg.inv(covMat), lPoints - mean))
return factor1*factor2
if __name__ == '__main__':
points = np.array([[-0.35, -0.15], [0.1, 0.1], [-0.1, 0.1], [0.05, 0.05],[0.25, 0.05], [0.1, 0.15], [0.1, 0.2], [-0.2, -0.2], [-0.25, 0.25], [0.45, 0.45], [0.75, 0.75], [0.6, 0.6], [0.55, 0.55], [0.7, 0.7], [0.68, 0.73]])
x1, y1 = createCells()
x = x1[0]
y = y1[:,0]
lP = np.array([])
numberOftimes = 0
for i in range(len(x) - 1):
for j in range(len(y) - 1):
count = 0
meanX = 0.0
meanY = 0.0
localPoints = []
covMat1 = np.array([])
covMat2 = np.array([])
for point in points:
inbetween_x = x[i] <= point[0] <= x[i + 1]
inbetween_y = y[j] <= point[1] <= y[j + 1]
if inbetween_x and inbetween_y:
count += 1
meanX += point[0]
meanY += point[1]
localPoints.append([point[0], point[1]])
if count >= 2:
numberOftimes += 1
#print(f"The local points are {localPoints}")
localPoints = np.array(localPoints)
meanX /= count
meanY /= count
meanXY = np.array([meanX, meanY])
#print(meanXY.shape)
#print(localPoints.shape)
lP = localPoints - meanXY
for k in range(count):
lPtranspose = (np.array([lP[k]])).T
lPCurrent = (np.array([lP[k]]))
if len(covMat1) > 0:
covMat1 += lPtranspose.dot(lPCurrent)
else:
covMat1 = lPtranspose*lP[k]
covMat1 /= count
lPoints = localPoints[..., np.newaxis] if lP.ndim == 2 else lP ## Create vectorized values for the x, y
meanXY1 = localPoints.mean(0)
meanXY2 = lPoints.mean(0)
covMat3 = np.einsum('ijk, ikj->jk', lPoints - meanXY2, lPoints - meanXY2) / lPoints[0] - 1
#yamlStatus = self.savingYaml(i, j, meanXY, covMat3) ## To store the cell parameters in a yaml file (for now its just out of scope for the question)
if np.linalg.det(covMat3) > 0: #compute the probability only if the det is not 0
Xx = np.linspace(x[i], x[i + 1], 1000)
Yy = np.linspace(y[i], y[i + 1], 1000)
Xx,Yy = np.meshgrid(Xx, Yy)
lPoints = np.vstack((Xx.flatten(), Yy.flatten())).T
pos = np.empty(Xx.shape + (2,))
pos[:, :, 0] = Xx
pos[:, :, 1] = Yy
z2 = probab(meanXY2, covMat3, lPoints)
summed = np.sum(z2)
z2 = z2.reshape(1000, 1000)
cs = plt.contourf(Xx, Yy, z2)#, cmap=cm.viridis)
plt.clabel(cs)
localPoints = []
#print(f"The number of times count is greater than 1 is {numberOftimes}")
plt.plot(x1, y1, marker='.', linestyle='none', markersize=20)
plt.plot(points[:,0 ], points[:, 1], marker='.', linestyle='none', markersize=10)
plt.grid(linewidth=0.5)#abs(x1[0][0]-y1[0][0]))
plt.show()

How to plot two different functions in the same graph in Python

I have this function:
from math import e
# f(x) = (e^3/3) - x
def ff(x):
return e**((x**3)/3 - x)
This is how its plot looks like using this code:
x = np.linspace(-3, 2.5, 100)
y = ff(x)
plt.plot(x, y)
plt.grid()
plt.show()
I have this other graph that it's the result of the following code:
def euler(x0,y,a,b,step):
listx = [x0]
listy = [y]
xn = x0
yn = y
while x0 < b:
y = y + step * f(x0, y)
x0 = x0 + step
if x0 > b:
break
listx.append(x0)
listy.append(y)
while xn > a:
yn = yn - step * f(xn, yn)
xn = xn - step
if xn < a:
break
listx.append(xn)
listy.append(yn)
return listx, listy
x, y = euler(step = 0.1, x0 = 0, y = 1, a = -3, b = 2.5)
plt.scatter(x, y, alpha = 0.5, s = 5)
plt.grid()
plt.xlim(-3, 2.5)
plt.show()
What I want to do is to plot both functions (euler and ff(x) functions) in the same graph. I've tried using the following code:
x, y = euler(step = 0.1, x0 = 0, y = 1, a = -3, b = 2.5)
plt.scatter(x, y, alpha = 0.5, s = 5)
x2 = np.linspace(-3, 2.5, 100)
y1 = ff(x)
plt.scatter(x2, y1)
plt.grid()
plt.xlim(-3, 2.5)
plt.show()
But I got this error:
unsupported operand type(s) for ** or pow(): 'list' and 'int'
I would really appreciate your help.
From your code, do you mean y1=ff(x2)? If you want x, you may want y1=ff(np.array(x)), but then plot y1 against x

Applying if-else one-liner on lists in Python

I have an array y that takes a value of either 0 or 1. Then I have an array yp that takes values between 0 and 1. The two arrays have the same length.
If an entry in y is 1, then I want to append the corresponding yp to a list, otherwise I want to append 1-yp:
y = [1,1,1,0,0]
yp = [0.1, 0.2, 0.3, 0.4, 0.5]
x = []
for idx, i in enumerate(y):
if i:
x.append(yp[idx])
else:
x.append(1-yp[idx])
Is there a shorter way to write this in Python, perhaps without a for-loop?
You can use a list comprehension with zip to iterate over both lists simultaneously:
>>> y = [1,1,1,0,0]
>>> yp = [0.1, 0.2, 0.3, 0.4, 0.5]
>>> [b if a else 1 - b for a, b in zip(y, yp)]
[0.1, 0.2, 0.3, 0.6, 0.5]
Perhaps you are looking for something like this if I understand you correctly?
for idx, i in enumerate(y):
x.append(yp[idx]) if i else x.append(1-yp[idx])
More like a ternary operation approach?
Reference: http://book.pythontips.com/en/latest/ternary_operators.html
If your lists are very long, there's a more efficient way using numpy:
y, yp = map(np.asarray, (y, yp) # convert to an array
x = y * yp + (1 - y) * (1 - yp)
The code above, explained:
a = y * yp: results in an array with the same length as y (and yp) with 1 * yp where y = 1 and 0 where y = 0.
b = (1 - y) * (1 - yp): results in an array with 1-yp where y=0 and 0 where y = 1.
a + b is the pairwise sum and yields your expected result.
You are asking for list comprehension (what you call "one-liner" ??) such as :
y = [1,1,1,0,0]
yp = [0.1, 0.2, 0.3, 0.4, 0.5]
l=[yp[i] if y[i]==1 else 1-yp[i] for i in range(len(y))]
whill give you :
>>> l
[0.1, 0.2, 0.3, 0.6, 0.5]

Find the shortest distance between a point and line segments (not line)

I have set of line segments (not lines), (A1, B1), (A2, B2), (A3, B3), where A,B are ending points of the line segment. Each A and B has (x,y) coordinates.
QUESTION:
I need to know the shortest distance between point O and line segments as shown in the shown figure implemented in line of codes. The code I can really understand is either pseudo-code or Python.
CODE: I tried to solve the problem with this code, unfortunately, it does not work properly.
def dist(A, B, O):
A_ = complex(*A)
B_ = complex(*B)
O_= complex(*O)
OA = O_ - A_
OB = O_ - B_
return min(OA, OB)
# coordinates are given
A1, B1 = [1, 8], [6,4]
A2, B2 = [3,1], [5,2]
A3, B3 = [2,3], [2, 1]
O = [2, 5]
A = [A1, A2, A3]
B = [B1, B2, B3]
print [ dist(i, j, O) for i, j in zip(A, B)]
Thanks in advance.
Here is the answer. This code belongs to Malcolm Kesson, the source is here. I provided it before with just link itself and it was deleted by the moderator. I assume that the reason for that is because of not providing the code (as an answer).
import math
def dot(v,w):
x,y,z = v
X,Y,Z = w
return x*X + y*Y + z*Z
def length(v):
x,y,z = v
return math.sqrt(x*x + y*y + z*z)
def vector(b,e):
x,y,z = b
X,Y,Z = e
return (X-x, Y-y, Z-z)
def unit(v):
x,y,z = v
mag = length(v)
return (x/mag, y/mag, z/mag)
def distance(p0,p1):
return length(vector(p0,p1))
def scale(v,sc):
x,y,z = v
return (x * sc, y * sc, z * sc)
def add(v,w):
x,y,z = v
X,Y,Z = w
return (x+X, y+Y, z+Z)
# Given a line with coordinates 'start' and 'end' and the
# coordinates of a point 'pnt' the proc returns the shortest
# distance from pnt to the line and the coordinates of the
# nearest point on the line.
#
# 1 Convert the line segment to a vector ('line_vec').
# 2 Create a vector connecting start to pnt ('pnt_vec').
# 3 Find the length of the line vector ('line_len').
# 4 Convert line_vec to a unit vector ('line_unitvec').
# 5 Scale pnt_vec by line_len ('pnt_vec_scaled').
# 6 Get the dot product of line_unitvec and pnt_vec_scaled ('t').
# 7 Ensure t is in the range 0 to 1.
# 8 Use t to get the nearest location on the line to the end
# of vector pnt_vec_scaled ('nearest').
# 9 Calculate the distance from nearest to pnt_vec_scaled.
# 10 Translate nearest back to the start/end line.
# Malcolm Kesson 16 Dec 2012
def pnt2line(pnt, start, end):
line_vec = vector(start, end)
pnt_vec = vector(start, pnt)
line_len = length(line_vec)
line_unitvec = unit(line_vec)
pnt_vec_scaled = scale(pnt_vec, 1.0/line_len)
t = dot(line_unitvec, pnt_vec_scaled)
if t < 0.0:
t = 0.0
elif t > 1.0:
t = 1.0
nearest = scale(line_vec, t)
dist = distance(nearest, pnt_vec)
nearest = add(nearest, start)
return (dist, nearest)
Rather than using a for loop, you can vectorize these operations and get much better performance. Here is my solution that allows you to compute the distance from a single point to multiple line segments with vectorized computation.
def lineseg_dists(p, a, b):
"""Cartesian distance from point to line segment
Edited to support arguments as series, from:
https://stackoverflow.com/a/54442561/11208892
Args:
- p: np.array of single point, shape (2,) or 2D array, shape (x, 2)
- a: np.array of shape (x, 2)
- b: np.array of shape (x, 2)
"""
# normalized tangent vectors
d_ba = b - a
d = np.divide(d_ba, (np.hypot(d_ba[:, 0], d_ba[:, 1])
.reshape(-1, 1)))
# signed parallel distance components
# rowwise dot products of 2D vectors
s = np.multiply(a - p, d).sum(axis=1)
t = np.multiply(p - b, d).sum(axis=1)
# clamped parallel distance
h = np.maximum.reduce([s, t, np.zeros(len(s))])
# perpendicular distance component
# rowwise cross products of 2D vectors
d_pa = p - a
c = d_pa[:, 0] * d[:, 1] - d_pa[:, 1] * d[:, 0]
return np.hypot(h, c)
And some tests:
p = np.array([0, 0])
a = np.array([[ 1, 1],
[-1, 0],
[-1, -1]])
b = np.array([[ 2, 2],
[ 1, 0],
[ 1, -1]])
print(lineseg_dists(p, a, b))
p = np.array([[0, 0],
[1, 1],
[0, 2]])
print(lineseg_dists(p, a, b))
>>> [1.41421356 0. 1. ]
[1.41421356 1. 3. ]
The explanation is in the docstring of this function:
def point_to_line_dist(point, line):
"""Calculate the distance between a point and a line segment.
To calculate the closest distance to a line segment, we first need to check
if the point projects onto the line segment. If it does, then we calculate
the orthogonal distance from the point to the line.
If the point does not project to the line segment, we calculate the
distance to both endpoints and take the shortest distance.
:param point: Numpy array of form [x,y], describing the point.
:type point: numpy.core.multiarray.ndarray
:param line: list of endpoint arrays of form [P1, P2]
:type line: list of numpy.core.multiarray.ndarray
:return: The minimum distance to a point.
:rtype: float
"""
# unit vector
unit_line = line[1] - line[0]
norm_unit_line = unit_line / np.linalg.norm(unit_line)
# compute the perpendicular distance to the theoretical infinite line
segment_dist = (
np.linalg.norm(np.cross(line[1] - line[0], line[0] - point)) /
np.linalg.norm(unit_line)
)
diff = (
(norm_unit_line[0] * (point[0] - line[0][0])) +
(norm_unit_line[1] * (point[1] - line[0][1]))
)
x_seg = (norm_unit_line[0] * diff) + line[0][0]
y_seg = (norm_unit_line[1] * diff) + line[0][1]
endpoint_dist = min(
np.linalg.norm(line[0] - point),
np.linalg.norm(line[1] - point)
)
# decide if the intersection point falls on the line segment
lp1_x = line[0][0] # line point 1 x
lp1_y = line[0][1] # line point 1 y
lp2_x = line[1][0] # line point 2 x
lp2_y = line[1][1] # line point 2 y
is_betw_x = lp1_x <= x_seg <= lp2_x or lp2_x <= x_seg <= lp1_x
is_betw_y = lp1_y <= y_seg <= lp2_y or lp2_y <= y_seg <= lp1_y
if is_betw_x and is_betw_y:
return segment_dist
else:
# if not, then return the minimum distance to the segment endpoints
return endpoint_dist
Basic algorithm: pretend that you have lines, so oriented that A lies to the left of B when O lies above the line (mentally rotate the picture to match as needed).
Find closest point as normal. If the point is between A and B, you're done. If it's to the left of A, the closest point is A. If the point is to the right of B, the closest point is B.
The case when A, B, and O all lie on the same line may or may not need special attention. Be sure to include a few tests of this position.
On my side, I've found that the two other answers were broken, especially when the line is purely vertical or horizontal. Here is what I did to properly solve the problem.
Python code:
def sq_shortest_dist_to_point(self, other_point):
dx = self.b.x - self.a.x
dy = self.b.y - self.a.y
dr2 = float(dx ** 2 + dy ** 2)
lerp = ((other_point.x - self.a.x) * dx + (other_point.y - self.a.y) * dy) / dr2
if lerp < 0:
lerp = 0
elif lerp > 1:
lerp = 1
x = lerp * dx + self.a.x
y = lerp * dy + self.a.y
_dx = x - other_point.x
_dy = y - other_point.y
square_dist = _dx ** 2 + _dy ** 2
return square_dist
def shortest_dist_to_point(self, other_point):
return math.sqrt(self.sq_shortest_dist_to_point(other_point))
A test case:
def test_distance_to_other_point(self):
# Parametrize test with multiple cases:
segments_and_point_and_answer = [
[Segment(Point(1.0, 1.0), Point(1.0, 3.0)), Point(2.0, 4.0), math.sqrt(2.0)],
[Segment(Point(1.0, 1.0), Point(1.0, 3.0)), Point(2.0, 3.0), 1.0],
[Segment(Point(0.0, 0.0), Point(0.0, 3.0)), Point(1.0, 1.0), 1.0],
[Segment(Point(1.0, 1.0), Point(3.0, 3.0)), Point(2.0, 2.0), 0.0],
[Segment(Point(-1.0, -1.0), Point(3.0, 3.0)), Point(2.0, 2.0), 0.0],
[Segment(Point(1.0, 1.0), Point(1.0, 3.0)), Point(2.0, 3.0), 1.0],
[Segment(Point(1.0, 1.0), Point(1.0, 3.0)), Point(2.0, 4.0), math.sqrt(2.0)],
[Segment(Point(1.0, 1.0), Point(-3.0, -3.0)), Point(-3.0, -4.0), 1],
[Segment(Point(1.0, 1.0), Point(-3.0, -3.0)), Point(-4.0, -3.0), 1],
[Segment(Point(1.0, 1.0), Point(-3.0, -3.0)), Point(1, 2), 1],
[Segment(Point(1.0, 1.0), Point(-3.0, -3.0)), Point(2, 1), 1],
[Segment(Point(1.0, 1.0), Point(-3.0, -3.0)), Point(-3, -1), math.sqrt(2.0)],
[Segment(Point(1.0, 1.0), Point(-3.0, -3.0)), Point(-1, -3), math.sqrt(2.0)],
[Segment(Point(-1.0, -1.0), Point(3.0, 3.0)), Point(3, 1), math.sqrt(2.0)],
[Segment(Point(-1.0, -1.0), Point(3.0, 3.0)), Point(1, 3), math.sqrt(2.0)],
[Segment(Point(1.0, 1.0), Point(3.0, 3.0)), Point(3, 1), math.sqrt(2.0)],
[Segment(Point(1.0, 1.0), Point(3.0, 3.0)), Point(1, 3), math.sqrt(2.0)]
]
for i, (segment, point, answer) in enumerate(segments_and_point_and_answer):
result = segment.shortest_dist_to_point(point)
self.assertAlmostEqual(result, answer, delta=0.001, msg=str((i, segment, point, answer)))
Note: I assume this function is inside a Segment class.
In case your line is infinite, don't limit the lerp from 0 to 1 only, but still at least provide two distinct a and b points.
I had to solve this problem as well, so for the sake of availability I'll post my code here. I did some cursory validation but nothing particularly serious. Your question actually helped me identify a bug in mine where a vertical or horizontal line segment would have broken the code and bypassed the intersection point on segment logic.
from math import sqrt
def dist_to_segment(ax, ay, bx, by, cx, cy):
"""
Computes the minimum distance between a point (cx, cy) and a line segment with endpoints (ax, ay) and (bx, by).
:param ax: endpoint 1, x-coordinate
:param ay: endpoint 1, y-coordinate
:param bx: endpoint 2, x-coordinate
:param by: endpoint 2, y-coordinate
:param cx: point, x-coordinate
:param cy: point, x-coordinate
:return: minimum distance between point and line segment
"""
# avoid divide by zero error
a = max(by - ay, 0.00001)
b = max(ax - bx, 0.00001)
# compute the perpendicular distance to the theoretical infinite line
dl = abs(a * cx + b * cy - b * ay - a * ax) / sqrt(a**2 + b**2)
# compute the intersection point
x = ((a / b) * ax + ay + (b / a) * cx - cy) / ((b / a) + (a / b))
y = -1 * (a / b) * (x - ax) + ay
# decide if the intersection point falls on the line segment
if (ax <= x <= bx or bx <= x <= ax) and (ay <= y <= by or by <= y <= ay):
return dl
else:
# if it does not, then return the minimum distance to the segment endpoints
return min(sqrt((ax - cx)**2 + (ay - cy)**2), sqrt((bx - cx)**2 + (by - cy)**2))

Python: A more Pythonic way to loop through grid classifications

I have an 11-by-11 size grid that is placed over a scatter plot. The scatter plot is of 100 randomly generated pairs. Within each grid space, is a classification type, where:
Type A is greater than 0, but less than 0.5 in both the X and Y axes,
Type B is greater than 0.5, but less than 1.5 in both the X and Y axes
ect...
I want to know how many points are within each grid space, as well as the pairs that exist in that grid space. This part isn't a problem, I just want to know if there is a more pythonic way to write my loop, since I don't want to have to write an if statement for each grid space.
My script is as follows:
TypeA = []
TypeB = []
fig = plt.figure()
ax = fig.gca()
ax.set_xticks(np.arange(0.5, 10.5, 1))
ax.set_yticks(np.arange(0.5, 10.5, 1))
for ii in range(100):
RNumX = randint(0, 10)
RNumY = randint(0, 10)
print RNumX, RNumY
hold(True)
plot1 = plt.scatter(RNumX, RNumY)
if RNumX >= 0 and RNumX < 0.5:
if RNumY >= 0 and RNumY < 0.5:
PairA = (RNumX, RNumY)
TypeA.append(PairA)
elif RNumY >= 0.5 and RNumY < 1.5:
PairB = (RNumX, RNumY)
TypeB.append(PairB)
SumA = len(TypeA)
SumB = len(TypeB)
print TypeA, SumA
print TypeB, SumB
plt.grid()
plt.show()
You could make Type a matrix and round the values to find your indices:
from random import random
# An 11 x 11 matrix of lists
Type = 11 * (11 * ([],),)
fig = plt.figure()
ax = fig.gca()
ax.set_xticks(np.arange(0.5, 10.5, 1))
ax.set_yticks(np.arange(0.5, 10.5, 1))
for ii in range(100):
# If you want to use floats in stead of ints
RNumX = 0.5 + 10 * random()
RNumY = 0.5 + 10 * random()
print RNumX, RNumY
hold(True)
plot1 = plt.scatter(RNumX, RNumY)
# Round the coordinates to find the indices
Type[int(RNumX + 0.5)][int(RNumY + 0.5)].append((RNumX, RNumY))
# Print all buckets as your snippet implies
for x in Type:
for y in x:
print y, len(y)
# Print only buckets with both values in the same range as your question implies
for x in range(11):
print Type[x][x], len(Type[x][x])
plt.grid()
plt.show()
you could use the bisect module to avoid those if statements. Here is a quick-and-dirty example.
from functools import total_ordering
import bisect
#total_ordering
class Point:
def __init__(self, X, Y):
self.X = X
self.Y = Y
def __eq__(self, other):
return self.X == other.X and self.Y == other.Y
def __lt__(self, other):
return self.X < other.X and self.Y < other.Y
print [(float(x)/2, float(x)/2) for x in xrange(0, 23)]
[(0.0, 0.0), (0.5, 0.5), (1.0, 1.0), (1.5, 1.5), (2.0, 2.0), (2.5, 2.5), (3.0, 3.0), (3.5, 3.5), (4.0, 4.0), (4.5, 4.5), (5.0, 5.0), (5.5, 5.5), (6.0, 6.0), (6.5, 6.5), (7.0, 7.0), (7.5, 7.5), (8.0, 8.0), (8.5, 8.5), (9.0, 9.0), (9.5, 9.5), (10.0, 10.0), (10.5, 10.5), (11.0, 11.0)]
points = [Point(float(x)/2, float(x)/2) for x in xrange(0, 23)]
types = [chr(x) for x in xrange(65, 91)]
print types
['A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z']
print types[bisect.bisect(points, Point(0.1, 0.1)) - 1]
A
print types[bisect.bisect(points, Point(0.6, 0.6)) - 1]
B

Categories

Resources