How to properly plot graph using matplotlib? - python

I have these two lists:
**l1** = ['100.00', '120.33', '140.21', '159.81', '179.25', '183.13', '202.49', '202.89', '204.18', '205.35', '206.44', '207.45', '208.40', '209.30', '210.15', '210.96', '211.73', '212.47', '213.18', '213.87', '214.53', '215.17', '215.79', '216.39', '216.98', '217.54', '218.10', '218.63', '219.16', '219.67', '220.18', '220.67', '221.15']
**l2** = ['13.14', '13.37', '13.53', '13.66', '13.76', '13.77', '20.70', '21.51', '23.85', '26.39', '29.13', '32.06', '35.17', '38.47', '41.95', '45.63', '49.50', '53.59', '57.90', '62.45', '67.25', '72.33', '77.70', '83.40', '89.43', '95.83', '102.65', '109.90', '117.65', '125.95', '134.84', '144.40', '154.71']
I plot l1 against l2 and this is what it's supposed to come out:
should_be
I use the following code:
fig, ax = plt.subplots(1)
ax.plot(l1, l2)
plt.show()
and this is what comes out it_is
like the step is regular even if the values are not equally distributed. Thanks

The problem here is that the list contain a string of values, however they must be a list of integer/float values. I also do not think you need subplots unless you want to have more than one plot. Below I have modified and executed the same and it works:
import matplotlib.pyplot as plt
l1 = [100.00, 120.33, 140.21, 159.81, 179.25, 183.13, 202.49, 202.89, 204.18, 205.35, 206.44, 207.45, 208.40, 209.30, 210.15, 210.96, 211.73, 212.47, 213.18, 213.87, 214.53, 215.17, 215.79, 216.39, 216.98, 217.54, 218.10, 218.63, 219.16, 219.67, 220.18, 220.67, 221.15]
l2 = [13.14, 13.37, 13.53, 13.66, 13.76, 13.77, 20.70, 21.51, 23.85, 26.39, 29.13, 32.06, 35.17, 38.47, 41.95, 45.63, 49.50, 53.59, 57.90, 62.45, 67.25, 72.33, 77.70, 83.40, 89.43, 95.83, 102.65, 109.90, 117.65, 125.95, 134.84, 144.40, 154.71]
plt.plot(l1, l2)
plt.show()
Output:

Have you tried to limited the views of the graph?
plt.xlim([25, 50])
or maybe, the axe range of them.
You can see more about it in this link:
https://stackabuse.com/how-to-set-axis-range-xlim-ylim-in-matplotlib/.

Have you tried using this?
%matplotlib inline
those graphs don't typically show up unless you have that line above where it's rendering.

Related

How to Order Coordinates in Matplotlib (xticks and yticks)

Alright, so I was working on a simple program to just pull coordinates out of a text pad and then graph what was in the text pad on a graph. I thought it would be pretty simple, but I am VERY new to matplotlib, so I still don't fully understand. I got most of the code done correctly, but the only thing that is not working is that when I put the values in the graph, they come all out of order. I want to order the xticks and yticks so that it actually looks like a real line graph you'd see in math, so you can see how the lower coordinates lower than the higher coordinates, and vice versa. Here is my code:
import matplotlib
import matplotlib.pyplot as plt
import numpy as np
def split(word):
return list(word)
fileIWant = open('C:/Users/JustA/Desktop/Python Shenanigans/Converting Coordinates in a .txt to a Graph/Coordinates.txt', 'r');
stopwords = ['\n']
array = fileIWant.readlines()
array = [array.replace('\n', '') for array in array if array not in stopwords]
fileIWant.close()
editFile = open('C:/Users/JustA/Desktop/Python Shenanigans/Converting Coordinates in a .txt to a Graph/Coordinates.txt', 'w')
array_length = len(array)
x = []
y = []
for i in range(array_length):
dataSplit = array[i].split()
getCoordinateX = dataSplit[1]
getCoordinateY = dataSplit[3]
x.append(getCoordinateX)
y.append(getCoordinateY)
plt.scatter(x, y)
plt.plot(x, y) #Add this line in if you want to show lines.
plt.title('Your Coordinate Graph')
plt.xlabel('X Coordinates')
plt.ylabel('Y Coordinates')
#plt.xticks([-100,-80,-60,-40,-20,0,20,40,60,80,100])
#plt.yticks([-100,-80,-60,-40,-20,0,20,40,60,80,100])
plt.show()
editFile.close()
I commented out what I put for the ticks, because it was not working at all. With those commented out, it looks okay, but it is very confusing. I think it just puts them in the order they are at in the .txt, when I want them to order themselves in the code. Here is what it is outputting right now:
Sorry if this is so simple that it has never been asked before, like I said, very new to matplotlib, and numpy if I have to use that at all. I imported it because I thought I may have to, but I don't think I really used it as of yet. Also, I am going to rewrite the coordinates into the graph in order, but I think I can do that myself later.
The problem is that your coordinates are strings, which means matplotlib is just plotting strings against strings ("categorical" axis labels). To fix, you simply have to convert your strings to numbers, e.g. x.append(int(getCoordinateX)).
Note that you also don't have to put plt.scatter/plt.plot in the loop - you only have to call one of those once on the full array. That'll probably make things a little faster too.

How to make Plt.plot show my parabolic line in python?

Maybe this will be duplicate question but I couldn't find any solution for this.
Normally what I coded should show me a curved line in python. But with this code I cant see it. Is there a problem with my code or pycharm ? This code only shows me an empty graphic with the correct axes.
And I did adding "ro" in plt.plot(at[i], st, "ro"). This showed me the spots on the graph but what I want to see the complete line.
at = [0,1,2,3,4,5,6]
for i in range(len(at)):
st = at[i]**2
plt.plot(at[i], st)
plt.show()
This is how you would normally do this:
import numpy as np
import matplotlib.pyplot as plt
at = np.array([0,1,2,3,4,5,6])
at2 = at ** 2
plt.plot(at,at2)
plt.show()
you can use something like plt.plot(at,at2, c='red', marker='o') to see the spots.
for detailed explanation please read the documentation.
Maybe rather calculate the to be plotted values entirely before plotting.
at = [0,1,2,3,4,5,6]
y = [xi**2 for xi in at]
plt.plot(at, y)
Or do it alternatively with a function
from math import pow
at = [0,1,2,3,4,5,6]
def parabolic(x):
return [pow(xi,2) for xi in x]
plt.plot(at, parabolic(at))
both return the following plot:
the other answers give fixes for your question, but don't tell you why your code is not working.
the reason for not "seeing anything" is that plt.plot(at[i], st) was trying to draw lines between the points you give it. but because you were only ever giving it single values it didn't have anything to draw lines between. as a result, nothing appeared on the plot
when you changed to call plt.plot(at[i], st, 'ro') you're telling it to draw single circles at points and these don't go between points so would appear
the other answers showed you how to pass multiple values to plot and hence matplotlib could draw lines between these values.
one of your comments says "its not parabolic still" and this is because matplotlib isn't a symbolic plotting library. you just give it numeric values and it draws these onto the output device. sympy is a library for doing symbolic computation and supports plotting, e.g:
from sympy import symbols, plot
x = symbols('x')
plot(x**2, (x, 0, 6))
does the right thing for me. the current release (1.4) doesn't handle discontinuities, but this will be fixed in the next release

How to overplot arrays of different shape?

I'm trying to overplot two arrays with different shapes but I'm unable to project one on the top of the other. For example:
#importing the relevant packages
import numpy as np
import matplotlib.pyplot as plt
def overplot(data1,data2):
'''
This function should make a contour plot
of data2 over the data1 plot.
'''
#creating the figure
fig = plt.figure()
#adding an axe
ax = fig.add_axes([1,1,1,1])
#making the plot for the
#first dataset
ax.imshow(data1)
#overplotting the contours
#for the second dataset
ax.contour(data2, projection = data2,
levels = [0.5,0.7])
#showing the figure
plt.show(fig)
return
if __name__ == '__main__':
'''
testing zone
'''
#creating two mock datasets
data1 = np.random.rand(3,3)
data2 = np.random.rand(9,9)
#using the overplot
overplot(data1,data2)
Currently, my output is something like:
While what I actually would like is to project the contours of the second dataset into the first one. This way, if I got images of the same object but with different resolution for the cameras I would be able to do such plots. How can I do that?
Thanks for your time and attention.
It's generally best to make the data match, and then plot it. This way you have complete control over how things are done.
In the simple example you give, you could use repeat along each axis to expand the 3x3 data to match the 9x9 data. That is, you could use, data1b = np.repeat(np.repeat(data1, 3, axis=1), 3, axis=0) to give:
But for the more interesting case of images, like you mention at the end of your question, then the axes probably won't be integer multiples and you'll be better served by a spline or other type interpolation. This difference is an example of why it's better to have control over this yourself, since there are many ways to to this type of mapping.

Matplotlib pyplot: plotting array mixes up y axis labels

I'm making a simple program in Python to plot two lists of integers, one data one the time axis.
The time list goes from 0 to 3 in increments of 1, while the data list consists of: 5,10, 3,12. I used print statements to verify that the lists do have the values mentioned above.
plt.plot(time_axis,data_array, 'ro')
plt.axis([0, 20, 0, 20])
plt.show()
However, as shown in the image, the plot y axis is labeled in the order that my data list is processed, not in ascending order: 5,10,3,12
Is there a way to make the y axis go in equal increasing increments upto 20?
EDIT: I noticed that this mixup only happens when i use the list as a parameter: eg,
plt.plot([0,1,2,3],[5,10,3,12],'bo') #gives the correct graph while
plt.plot(time_axis,data_array,'bo') #gives the incorrect graph,
Even though the two lists time_axis and data_array contain the same values.
Tracing back my error, I was importing my data values from a text file, and the parsing was done incorrectly, so the data values were not ints. The char values were in the format '5\n',etc so numplot was getting confused. Fixing that solved the issue!
I feel like you're omitting the code which is making this screwy, but here's what I did:
import matplotlib.pyplot as plt
time_axis = range(0,4)
data_array=[5,10,3,12]
plt.plot(time_axis,data_array, 'ro')
plt.axis([0, 20, 0, 20])
plt.show()
This produces the image:
which seems to be what you were aiming for.

How to use matplotlib to plot only the last 50 values of growling lists?

I am trying to use matplotlib function in Python to interactively plot only the last 50 values of 2 growing lists while a loop goes on. However, once the size of the lists grow to more than 50, the values of the plot lines start overlapping.
I want to clear the overlapping.
Here is the photo of the plot at iteration < 50. Nice and clean.
Here is the photo of the plot at iteration > 50. You can see that it's getting messy.
Here is my code
import matplotlib.pyplot as plt
ls1 = []
ls2 = []
while True:
(some computation to get, in every iteration, 2 new values: ls1_new and ls2_new)
ls1.append(ls1_new)
ls2.append(ls2_new)
plt.plot(ls1[-50:])
plt.plot(ls2[-50:])
plt.draw()
plt.pause(0.0001)
Can anyone help me solve the overlapping part? Thanks ahead for the help! :)
Your problem is that you are creating new lines at every iteration. It would probably be nicer to update your existing lines instead. The code below will probably won't work straight away, but it should point you in the right direction. The general idea is to keep a reference to the Line2D object returned by plt.plot() and then using the member functions Line2D.set_data(x, y) or Line2D.set_ydata(y) to update the line at each iteration.
import matplotlib.pyplot as plt
ls1 = []
ls2 = []
l1, = plt.plot([])
l2, = plt.plot([])
while True:
(some computation to get, in every iteration, 2 new values: ls1_new and ls2_new)
ls1.append(ls1_new)
ls2.append(ls2_new)
l1.set_data(range(50),ls1[-50:])
l2.set_data(range(50),ls2[-50:])
plt.draw()
plt.pause(0.0001)

Categories