# Is there a formula for an s-shaped curve with domain and range [0,1]?

Basically I want to convert similarity measures into weights which are used as predictors. The similarities will be on [0,1], and I will restrict the weights to also be on [0,1]. I'd like a parametric function that does this mapping which I'll likely optimize using gradient descent. The requirements are that 0 maps to 0, 1 maps to 1 and it be strictly increasing. A simple derivative is also appreciated.

Edit: Thanks for the responses so far, those are very helpful. To make my purpose more clear, the task is prediction. My observations are extremely sparse vectors with a single dimension to predict on. My input dimensions are used to compute similarity. My prediction is then a weighted sum of other observations' value for the predictor where the weight is a function of similarity. I'm bounding my weights on [0,1] for simplicity. It is hopefully obvious now why I require 0 to map to 0, 1 to map to 1, and for it to be strictly increasing. As whuber has pointed out using f(x) =x meets these requirements and actually works pretty well. However it has no parameters to optimize. I have lots of observations so I can tolerate a lot of parameters. I'll be hand coding the gradient descent, hence my preference for a simple derivative.

For example, much of the responses given are symmetric about .5. It would be useful to have parameter to shift left/right (such as with the beta distribution)

• $f(x)=x$ satisfies every one of your requirements.
– whuber
May 26, 2016 at 21:04
• I've added a little in response to your edit about controlling the shift left-right. All three example families in my picture have a direct way to control that. May 28, 2016 at 1:34

Here's one:

$y=\frac{1}{1+\left ( \frac{x}{1-x} \right )^{-\beta}}$

where $\beta$ is $>0$

]2

• Is this a standard function like the $tanh$ of $sin$? I am interested to identify it in the wed but I could not. Could you please give a reference? Jan 8, 2018 at 10:39
• Hi Darkmoor, I got this equaion by playing around with the "inverse logit function". You can see that it resembles y=inverse logit (x) = 1 / (1 + e^-x) Because logit maps to (0,1) imgur.com/a/H0kGF Jan 10, 2018 at 10:05
• You can add an extra level of adjustment so that you can tune the position at which the function is equal to .5 by using y=1/(1+(x^r/(1-x^r))^-b). Then, to attain y=.5 at x0 set r=-log(2)/log(x0). Or, if you want to ensure that y=k for some k between 0 and 1 at x=x0 then set r=-log((1/k - 1)^(1/b)+1)/log(x0) May 9, 2019 at 17:27
• Numerically stable formulation: f(x) = x^b/(x^b + (1-x)^b) Nov 12, 2022 at 16:48

What you're trying to use this for is not particularly clear to me so I can't say whether it makes sense to do but fulfilling all your criteria seems to be fairly trivial.

• s-shaped curve

• parametric function

• 0 maps to 0, 1 maps to 1, strictly increasing

• simple derivative

So why not just take any convenient specific family of continuous unimodal* distribution functions on [0,1] whose pdf is "simple"? That seems to fulfill every part of what you list there.

* (whose mode is bounded away from the endpoints)

• s-shaped curve - guaranteed by unimodality (with mode not at endpoints)

• parametric - by giving any specific family which has parameters

• 0 maps to 0, 1 maps to 1 strictly increasing - that's what distribution functions on [0,1] do; you just need the density to be >0 in (0,1)

• simple derivative -- that's the pdf, so if the pdf is "simple" by whatever criterion suits you, you're done.

There are (as Alex R stated) an infinite number of these. The beta he mentions is an obvious one, but the cdf is the incomplete beta function, so you'd need something to evaluate that --- it's a standard function in many packages (including almost all decent stats packages) so I doubt that will be difficult. Note however that not all betas are unimodal (with mode not at the ends), so the family also encompasses cdfs that are not "s" shaped.

Here are pictures of three reasonably simple families:

There are many other choices and new ones can easily be constructed.

--

In response to the edit to the question:

Note that all three of the families I drew pictures of have a a simple way to obtain left-right shifts (i) for the triangular distribution, the parameter directly moves the curve left or right (i.e. controls the degree of asymmetry, $$c=\frac12$$ is the symmetric case); for the logitnormal the $$\mu$$ parameter controls the asymmetry; for the beta distribution, the sign of $${\alpha-\beta}$$ (equivalently, the sign of $$\frac{\alpha}{\alpha+\beta}-\frac12$$) controls it.

As already commented by @whuber the function $f(x)=x$ satisfies the three requirements you mentioned (i.e. 0 maps to 0, 1 maps to 1 and the function is strictly increasing). In the title of your question, you seem to indicate that you are also interested in the function being S-shaped, as in Sigmoid/Logistic curve. Is this correct? In that case, you should certainly try the following logistic function which will approximately meet all 4 criteria you specified: $$\frac{1}{1+e^{-k(x-0.5)}}$$.

The $k$ in this equation will control the slope of your curve. Changing $k$ will also allow you to control how close $f(0)$ and $f(1)$ are to 0 and 1, respectively. For example for $k=20$, $f(0)=4.539787e-05$ and $f(1)=0.9999546$.

The derivative of this function is easily computed as:$$\frac{ke^{-k(x-0.5)}}{(1+e^{-k(x-0.5)})^2}$$ Further information on this function can be found at https://en.wikipedia.org/wiki/Logistic_function

• This function does not map 1 -> 1. In fact, f -> 1 as x -> ∞. Depending on k the value of f at x=1 may be quite small, but it will never be exactly 0. In fact, that is the main reason for using e^... in the denominator, i.e. so that the relevant domain is [0,∞) instead of [0,1]. May 13, 2019 at 18:11

Let me offer the most general solution consistent with the requirements: that will give you the most flexibility to choose and optimize.

We may interpret "S-shaped" as a monotonically increasing curve (because the transformation ought to be one-to-one) consisting of one part that is concave upwards and another part that is concave downwards. We may focus on making the left half concave down, because the other type (with left half concave up) is obtained through inverting such transformations.

Since the transformation $$f$$ is supposed to be differentiable, it must therefore have a decreasing derivative $$f^\prime$$ in the left half and an increasing derivative in the right half. Regardless, the derivative must be nonnegative and can be zero only at an isolated point (if at all: the minimum value of the derivative gives the least slope of the transformation.)

It is not required that the derivative be differentiable, but as a practical matter we may suppose that it is differentiable almost everywhere with derivative $$f^{\prime\prime}$$.

This second derivative can do practically anything: all we require is that

• it is integrable,

• is less than or equal to zero for all values in some left-hand interval $$[0, k)$$, and

• is greater than or equal to zero for all values in the right hand interval $$(k, 1]$$.

Such functions $$f^{\prime\prime}$$ (and their inverses) parameterize the set of all solutions. (There is some redundancy: it is taken care of by a final normalization step described below.)

The Fundamental Theorem of Calculus enables us to recover $$f$$ from any such specification. That is,

$$f^\prime(x) = \int_0^x f^{\prime\prime}(t) dt$$

and

$$f(x) = \int_0^x f^\prime(t) dt.$$

The conditions on $$f^{\prime\prime}$$ guarantee that $$f$$ rises monotonically from its minimim $$f(0)$$ to some maximum $$f(1) = C$$. Finally, normalize $$f$$ by dividing the values of the preceding integral by $$C$$.

Here is an illustration starting with a version of a random walk for the second derivative. In it, the derivatives have not been normalized, but the transformation $$f$$ has been.

To apply this approach, you may begin with an analytic expression for $$f^{\prime\prime}$$, perhaps varied by a finite number of parameters. You may also specify it by giving some points along its graph and interpolating among them--provided that the interpolator respects the negativity of the values on $$[0,k)$$ and the positivity on $$(k,1]$$. The latter is the method used to generate the illustration. The corresponding R code (below) provides the details of the calculation.

This approach enables you to design any transformation you like. You could begin by sketching the S-curve, estimating its (relative) slopes $$f^\prime$$, and from that estimating its slopes. Specify some $$f^{\prime\prime}$$ to match that latter picture, then proceed to compute $$f^\prime$$ and then $$f$$.

Note that $$f$$ that are first concave up and then concave down can also be obtained by negating $$f^{\prime\prime}$$ at the outset. The critical condition for creating an S-shaped curve is that (apart from possible excursions on a set of measure zero) $$f^{\prime\prime}$$ may actually cross zero at most once.

Incidentally, the solution $$f(x)=x$$ arises by setting $$f^{\prime\prime}(x)=0$$ almost everywhere, making $$f^\prime$$ constant and positive, whence $$f$$ is linear; normalization assures the slope is $$1$$ and the intercept is $$0$$. (Making $$f^\prime$$ constant and negative produces the solution $$f(x)=1-x$$.)

    n <- 51                      # Number of interpolation points
k.1 <- floor(n * 2/3)        # Width of the left-hand interval
k.2 <- n - k.1               # ............ right-hand interval
x <- seq(0, 1, length.out=n) # x coordinates
set.seed(17)

# Generate random values of the second derivative that are first negative,
# then positive.  Modify to suit.
y.2 <- (c(runif(k.1, -1, 0), 0.5*runif(k.2, 0, 1))) *
abs(cos(3*pi * x)) +
c(rep(-.1, k.1), rep(.5,k.2))

# Recover the first derivative and then the transformation.
# Control the
# minimum slope of the transformation.
y.1 <- cumsum(y.2)
y.1 <- y.1 - min(y.1) + 0.005 * diff(range(y.1))
y <- cumsum(y.1)
y <- (y - y[1]) / (y[n] - y[1]) # Normalize the
# transformation

#
# Plot the graphs.
par(mfrow=c(1,3))
plot(x, y.2, type="l", bty="n", main="Second derivative")
points(x, y.2, pch=20, cex=0.5)
abline(h=0, col="Red", lty=3)
plot(x, y.1, type="l", bty="n", lwd=2, main="First
derivative")
abline(h=0, col="Red", lty=3)
plot(x, y, type="l", lwd=2, main="Transformation")