1

This is the function I need to plot: function

This is my code:

pi = np.pi
sin = np.sin
e = np.e

x1 = np.linspace(-10*pi, -pi)
y1 = (4*pi*(e**0.1*x1)) * sin(2*pi*x1)
plt.plot(x1, y1)

x2 = np.linspace(-pi, -pi/2)
y2 = 0
plt.plot(x2, y2)

x3 = np.linspace(-pi/2, pi/2)
y3 = 4/pi * x3**2 - pi
plt.plot(x3, y3)

x4 = np.linspace(pi/2, pi)
y4 = 0
plt.plot(x4, y4)

plt.show()

But every time I try to run it gives me a ValueError:

ValueError: x and y must have same first dimension, but have shapes (50,) and (1,)

I have tried using np.piecewise but haven't gotten anywhere.

1
  • You are setting y2 and y4 to a single value of 0. Remember, you are not plotting functions. Even if y2 is always zero, you still need to create a list/array/whatever with all the necessary number of zeros [0, 0, and so on. Commented Nov 18, 2022 at 10:43

3 Answers 3

2

enter image description here

To define a piecewise function, I usually use a chained sequence of numpy.where.

First, the domain for the independent variable, then the conditions and the analytical expression, with a difference for the last where, as explained in the docs.
NB: are you sure that the circular frequency of the sines is 2π? when I see a domain expressed in multiples of π I think immediately to frequencies expressed as integer numbers or simple fractions…

from numpy import exp,linspace, pi, sin, where
from matplotlib.pyplot import grid, plot, show

x = linspace(-10*pi, +10*pi, 4001)
y = where(x <  -pi, 4*pi*exp(+x/10)*sin(1*x),
    where(x <-pi/2, 0,
    where(x <+pi/2, 4*x*x/pi-pi,
    where(x <  +pi, 0,
                    4*pi*exp(-x/10)*sin(1*x)))))
    
plot(x, y) ; grid() ; show()

PS

In a comment Davide_sd correctly remarks that the technique I have shown is OK only if the piecewise function is continuous.
If there are discontinuities across sub-domains, you can always use numpy.where but you should assign np.nan values to the y array in the points of discontinuity, so that Matplotlib knows that she has to break the line across the NaN.


EDIT — I've changed the circular frequency of the sines because I cannot make sense of the OP specification.

Sign up to request clarification or add additional context in comments.

4 Comments

Note that this will connects the point between two pieces, which might get the wrong idea to someone looking at the plot!
@Davide_sd Good general remark, but THIS function is continuous.
@Davide_sd I have edited my answer to incorporate/discuss your useful remark.
I like the structure of this approach. I will be doing piecewise polynomial fits.
0

x2 is an array, and y2 is a number, matplotlib expects both to be arrays, so you should switch y2 and y4 definition to be y2 = np.zeros_like(x2), and y4 = np.zeros_like(x4).

1 Comment

Thank you so much, I'm quite new to matplotlib
0

As x and y need to be the same first dimension, you might want to define y2 and y4 to be a function of x, so that an array of the same dimension is produced as a result to plot.

#...
y2 = x2*0
plt.plot(x2, y2)

#...

y4 = x4*0
plt.plot(x4, y4)

Alternatively, you could have y2 and y4 defined as an array of zeros of the same size of x2 and x4 respectively.

y2 = np.zeros(x2.shape)
y4 = np.zeros(x4.shape)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.