seaborn kdeplot x axis scaling? - seaborn

I have a histogram of my data:
h is a 1-d array of counts
x is a 1-d array of bin values
Now if I do:
sns.kdeplot(h, shade=True);
I get a plot where x-axis goes from -20 to 100, which has nothing to do with
my original x data. How do I get the x-axis scaled to match my data?

I see I misunderstood the input to kde. It wants the original values. I had already created a histogram and wanted to feed that to kde.
In my histogram I have h.buckets, and h.results. I did
def hist_to_values (hist):
ret = []
for x,y in zip (hist.buckets, h.results):
ret.extend ([x] * y)
return np.array (ret)
Then feed this to kde, and I got the results I expect.

Related

How to get a list of values out of a 2D point plot saved as pdf with Mathematica?

I have data that is only accessible as a 2D point plot saved as pdf-file and need the raw data (the x and associated y values) out of it.
Is there any way I can do this with Mathematica, so that I am able to use the data internally for evaluation?
An example plot to Import would be (ListPlot of x^2; x=0-10)
Here is an approach you could take with Mathematica
img = First#Import[
"https://drive.google.com/uc?export=download&id=1Kgny29eM8q2oIj7BopP-dx0HQ4E449P_"];
mb = MorphologicalBinarize[img];
cn = ColorNegate[Closing[mb, DiskMatrix[0.5]]];
coords = Flatten[Last /# ComponentMeasurements[cn, {"Centroid"}], 1];
ListPlot[coords]
You will have to appropriately scale the coordinates if you want them to exactly match y = x^2.

Seaborn Stripplot Axis Values with Correct Scaling

I'm trying to plot some data in seaborn where the x values are percentages*100 as floating point numbers (ie 90.909). When I make the plot:
fig, ax = plt.subplots(figsize=(10,10))
ax = sns.stripplot(df_12['% ident'], df_12['length'], jitter=True)
The decimals in the floating points make the X axis unreadable:
Initial Plot
I would like to set the x axis to show only whole number multiples of 5 (ie 80, 85, 90, 95, 100).
One method I have tried is the following:
fmt = '{:0.0f}'
xticklabels = []
count = 0
for item in ax.get_xticklabels():
count+= 1
item.set_text(fmt.format(float(item.get_text())));
xticklabels += [item];
ax.set_xticklabels(xticklabels);
This succeeds in changing the axis values to integers, but the axis looks busy. The numbers shown are also inconsistent between similar datasets.
Second Plot
I would like to reduce the total number of values shown on the axis. I have tried to use
ax.xaxis.set_major_locator(plt.MaxNLocator(5))
Or similarly
ax.xaxis.set_major_locator(plt.MaxNLocator(5))
ax.set_xticklabels([80, 85, 90, 95, 100])
Which give outputs similar to this:
Third Plot
If you compare this to the previous plot, you'll notice the x axis labels no longer relate to the points plotted. How do I set the values of the x axis while still keeping them related to the points plotted?
Other things I have tried:
ax.set_xlim(75, 100)
This and any variants result in a blank plot.
ax.set(xticklabels=[75,80,85,90,95,100])
Does the same thing where the axis labels don't match the data.
ax.set(xticks=range(75,101), xticklabels=[75,80,85,90,95,100])
Results in all the data points stuck on the left side of the plot with all the axis labels overlapping on a single tick on the right.
ax.xaxis.set_major_locator(ticker.MaxNLocator(integer=True))
This doesn't change the axis values to integers, and also appears to cause the axis to no longer correlate with the data.

How to get actual pixel indices from MATLAB function ginput?

I am using the MATLAB function ginput to label my image data for further process. Here is my code:
file_name = "test.jpg";
% Read the image
img = imread(file_name);
% Get the image dimension
imgInfo = imfinfo(file_name);
width = imgInfo.Width;
height = imgInfo.Height;
% Using ginput function to label the image
figure(1);
imshow(img);
hold on;
[x, y] = ginput(4); % Manually label 4 points
scatter(x, y, 100, 'ro', 'filled'); % Plot the marked points on img
hold off;
My Problem:
I found that the output x and yare not integers, so they are not representing the pixel indices.
Sometimes, these two conditions max(x) > width and max(y) > height are satisfied. It seems to suggest that the 4 points I marked using ginput are outside the image (but actually it is not).
I am aware of this issue is related to Image Coordinate System setting, but I am still not sure how to convert x and y obtained from ginput function to the actual pixel indices?
Thanks.
The code below shows a 2x2 image, enlarges the axes so we can see it, then turns on the axes ticks and labels. What this does is allow you to see the coordinate system used to render images in an axes object.
imshow([255,0;0,255])
set(gca,'position',[0.2,0.2,0.6,0.6])
axis on
The coordinates returned by ginput match these coordinates.
In short, what you need to do is simply round the coordinates returned by ginput to get indices into the image:
[x, y] = ginput(4); % Manually label 4 points
x = round(x);
y = round(y);

Getting the dimensions of a numpy array right to plot converted greyscale image

as part of Unity's ML Agents images fed to a reinforcement learning agent can be converted to greyscale like so:
def _process_pixels(image_bytes=None, bw=False):
s = bytearray(image_bytes)
image = Image.open(io.BytesIO(s))
s = np.array(image) / 255.0
if bw:
s = np.mean(s, axis=2)
s = np.reshape(s, [s.shape[0], s.shape[1], 1])
return s
As I'm not familiar enough with Python and especially numpy, how can I get the dimensions right for plotting the reshaped numpy array? To my understanding, the shape is based on the image's width, height and number of channels. So after reshaping there is only one channel to determine the greyscale value. I just didn't find a way yet to plot it yet.
Here is a link to the mentioned code of the Unity ML Agents repository.
That's how I wanted to plot it:
plt.imshow(s)
plt.show()
Won't just doing this work?
plt.imshow(s[..., 0])
plt.show()
Explanation
plt.imshow expects either a 2-D array with shape (x, y), and treats it like grayscale, or dimensions (x, y, 3) (treated like RGB) or (x, y, 4) (treated as RGBA). The array you had was (x, y, 1). To get rid of the last dimension we can do Numpy indexing to remove the last dimension. s[..., 0] says, "take all other dimensions as-is, but along the last dimension, get the slice at index 0".
It looks like the grayscale version has an extra single dimension at the end. To plot, you just need to collapse it, e.g. with np.squeeze:
plt.imshow(np.squeeze(s))

Change pixel values on a line in MATLAB

I wish to set values on a line whose endpoints are returned by the hough transforms to zero. I have written the following code snippet
imshow(img);
hold on
img_black = img;
for k = 1:length(lines)
xy = [lines(k).point1; lines(k).point2]; %line end points
[x, y] = bresenham(xy(1,1),xy(1,2),xy(2,1),xy(2,2)); %returns all points on the line
for i = 1:length(x)
plot(x(i),y(i),'*'); %to plot individual pixels on line itself
img_black(x(i),y(i),:) = [0,0,0]; %set rgb values to zero
end
end
Although the points plotted on the image below are as expected
The image where the corresponding pixel values are being set to zero is not as expected.
What is happening here?
It looks like you have mixed up x and y with rows and columns.
img_black(x(i), y(i),:)
Should be
img_black(y(i), x(i),:);
This is because the first dimension of img_black is rows (y) and the second dimension is columns (x).
The resulting image looks like it does because your lines go the wrong way and (sometimes) go outside the bounds of the original image, but MATLAB gladly expands your image (with zeros) and sets the values that you request, hence all the black pixels on the right.
NOTE: This switching back and forth between row, column and x,y is common throughout MATLAB's built-in functions and you should always be careful to note what the output is. A class example is meshgrid vs ndgrid outputs.

Resources