Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Customizable squashing function #3

Open
endolith opened this issue Dec 16, 2017 · 4 comments
Open

Customizable squashing function #3

endolith opened this issue Dec 16, 2017 · 4 comments

Comments

@endolith
Copy link
Owner

endolith commented Dec 16, 2017

Mapping [0, ∞) to [0, 1] can be done many different ways, and I found some worked better or worse for different functions.

I originally used mpmath.cplot for this, which combines squashing and colormapping into the same function default_color_function(), but maybe more logical to separate them? Like specify mapping and colormap as parameters to cplot, like matplotlib's norm parameter.

@nschloe
Copy link
Collaborator

nschloe commented Dec 19, 2017

At first I thought: Why map the interval at all? Real-valued plots simply take the min and max values of the function on the plotted domain and identify those values with the lower and upper end of the color map. We could do the same for abs(z). Done.

Then I realized that that identifying 0 with black and infinity with white has one very nice propery: Complex angles don't have meaning for 0 and infinity just like hue doesn't have meaning for black and white. This is a correspondence we should not simply let go. So yeah, let's map. :)

I'm not sure if I agree to make the map configurable though. Introducing one fixed map will make all plots made with complex_colormap comparable. If the map is configurable, users may be tempted to "highlight" certain aspects of their data, effectively distorting it and making the plot misleading.
One thing about a fixed map is one particular map presents itself naturally. In the current implementation,

J = (1.0 - (1 / (1.0 + np.abs(z)**0.3))) * 100

set 0.3 to 1 to get

x = abs(z)
J = x / (x + 1) * 100

@waldyrious
Copy link

Probably redundant, but I thought I'd mention this diagram which I often come back to for this sort of mapping (although most of the time I just end up using tanh):


(source)

The formula in @nschloe's comment above kind of matches the last one in the diagram,
with the difference that they do z / (abs(z) + 1), not abs(z) / (abs(z) + 1).

@nschloe
Copy link
Collaborator

nschloe commented Dec 20, 2017

One nice property of

x***alpha / (x**alpha + 1)

is that

f(x) = 1 - f(1/x)

This makes sure that when comparing inverses, e.g., tan(z) and 1/tan(z), whites and blacks are exactly inverted as well. This is not true for any of the depicted functions except x / (1+x). (This can easily be spotted by the fact that the curves don't go through (1, 0.5).)

@endolith
Copy link
Owner Author

If the map is configurable, users may be tempted to "highlight" certain aspects of their data, effectively distorting it and making the plot misleading.

That's what I do, though. 😅

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants