Code Monkey home page Code Monkey logo

Comments (5)

mkcor avatar mkcor commented on September 26, 2024

Hi @testor2897,

Thanks for reporting. In order to make your issue easier to investigate, would you mind replacing from math import * with an explicit import math and, perhaps, attach some plots to visualize data points?

from scikit-image.

testor2897 avatar testor2897 commented on September 26, 2024

Hi,

I removed import math from the example as it is unnecessary, sorry for confusion.

In order to make a visualization I produced a matplot-graph:

from pylab import *
from matplotlib.ticker import (MultipleLocator, FormatStrFormatter, AutoMinorLocator)

import numpy as np

try:
  from skimage.measure import EllipseModel
  scikitloaded = True
except:
  scikitloaded = False
  print("\nscikit not installed!\n")


# scale measuring data for optimized calculations
# move data central around average values
# scale numbers to <2
# return scaled data and scales
def scalePoints(x,y,enableMove=True,enableScale=True):

    if enableMove:
      # calculate average of x and y
      avgx = np.mean(x)
      avgy = np.mean(y)
    else:
      avgx = avgy = 0

    if enableScale:
      # calculating scale factors
      sfx = (np.max(x) - np.min(x))/2
      sfy = (np.max(y) - np.min(y))/2
      # uniform scale factor = max(sfx, sfy)
      # is easier for unscaling
      sfx = sfy = max(sfx, sfy)
      
    else:
      sfx = sfy = 1

    # creating scaled and centroid data points
    # in order to keep calculation results small
    x = (x - avgx)/sfx
    y = (y - avgy)/sfy
    return [x, y, avgx, avgy, sfx, sfy]


# https://stackoverflow.com/questions/39693869/fitting-an-ellipse-to-a-set-of-data-points-in-python
def fitEllipse(x,y, useScale=False):
    if useScale:
      # creating scaled and centroid data points
      # in order to keep calculation results small
      x, y, avgx, avgy, sfx, sfy = scalePoints(x,y)

    points = np.hstack([x, y])

    ell = EllipseModel()
    ell.estimate(points)
    if ell.params is None:
      return ell.params
      
    xc, yc, a, b, phi = ell.params

    if useScale:
      # unscale results
      xc = xc * sfx + avgx
      yc = yc * sfy + avgy
      a = a * sfx
      b = b * sfy
    
    return [xc, yc, a, b, phi]


def get_ellipse_pts(params, npts=100, tmin=0, tmax=2*np.pi):
    """
    Return npts points on the ellipse described by the params = x0, y0, ap,
    bp, phi for values of the parametric variable t between tmin and tmax.

    """

    x0, y0, ap, bp, phi = params
    # A grid of the parametric variable, t.
    t = np.linspace(tmin, tmax, npts)
    x = x0 + ap * np.cos(t) * np.cos(phi) - bp * np.sin(t) * np.sin(phi)
    y = y0 + ap * np.cos(t) * np.sin(phi) + bp * np.sin(t) * np.cos(phi)
    return x, y


titleSample = "pretty linear data"
xSample = np.array([3.0751, 2.9036, 2.7675, 2.6505, 2.5423, 2.4352])
ySample = np.array([3.2164, 3.133, 3.0626, 2.9991, 2.9378, 2.8748])

print("Data Points\nx:\n", xSample, "\ny:\n", ySample, "\n")
# Transpose Coordinates an make it 2 dimensional
xSample = xSample[:, np.newaxis]
ySample = ySample[:, np.newaxis]

fig, ax = plt.subplots()
plot(xSample, ySample, 'bo', label='data points')
xlabel('x')
ylabel('y')
ax.xaxis.set_minor_locator(AutoMinorLocator())
ax.yaxis.set_minor_locator(AutoMinorLocator())

# Prepare Plot
fig.canvas.manager.set_window_title('Fitting of Ellipses with data points')
fig.patch.set_facecolor('white')



if scikitloaded:
    # scale points for fit
    print("\nResult of estimate with scaled points:\n[xc, yc, a, b, phi]")
    para = fitEllipse(xSample,ySample, True)
    print(para)
    xx, yy = get_ellipse_pts(para)
    plot(xx, yy, 'g-' , linewidth = 1, label = "Result of estimate with scaled points")
    xc, yc = para[0:2]
    plot(xc, yc, 'k.')

    # do not scale points for fit
    print("\nResult of estimate without scaling:\n[xc, yc, a, b, phi]")
    para = fitEllipse(xSample,ySample, False)
    print(para)
    if para is not None:
        xx, yy = get_ellipse_pts(para)
        plot(xx, yy, 'r-' , linewidth = 1, label = "Result of estimate without scaling")
        xc, yc = para[0:2]
        plot(xc, yc, 'b.')

    # set general plot parameter
    legend(loc='lower right', labelcolor='linecolor', facecolor="darkgray")
    plt.show()

The points and results in console are:
image

There is the result None (no result or error) for the test without scaling.

Matplotlib (extended example) shows the following:
image

As there is no result for the test without scaling the example won't plot a graph.

from scikit-image.

mkcor avatar mkcor commented on September 26, 2024

Hi @testor2897,

Thank you. I think I get it. Basically, you recommend making the data values non-dimensional (falling in the interval [-1, 1]) before fitting the model. The result can be re-dimensionalized afterwards, indeed. As a physicist by training, I can't say no to that!

Would you be able/available to submit a PR updating skimage.measure.EllipseModel?

from scikit-image.

testor2897 avatar testor2897 commented on September 26, 2024

Hi mkcor,

unfortunately I am not familiar with PR updating (pull requests?) and had little time lately.

So I extracted the newest version of estimate (part of Class EllipseModel in fit.py) today and tested.
It seems that meanwhile the code was updated...
My new test was positive => parameters were produced: xc, yc, a, b, phi = Ellipse.params
and even a > b that is nice.
When will the new version be released?

from scikit-image.

mkcor avatar mkcor commented on September 26, 2024

Hi Sebastian,

unfortunately I am not familiar with PR updating (pull requests?) and had little time lately.

Yes, 'PR' means 'pull request' (pardon the abbreviation). I wasn't talking about 'PR updating' actually; I was talking about submitting a pull request which would update skimage.measure.EllipseModel (sorry that wasn't clear).

So I extracted the newest version of estimate (part of Class EllipseModel in fit.py) today and tested. It seems that meanwhile the code was updated...

You can always see whether code was updated or not, and when exactly, and by who. Here is the commit history for fit.py, i.e., the history of all changes which affected (at least one line of) this file. Here is the Git blame for fit.py, i.e., the detail of all changes for each line. I'm guessing that the code change you've noticed comes from PR #6703, which was merged on Mar 2, 2023 and landed in version 0.21.

You shared your version information in the first place (scikit-image version: 0.19.3) but I'm taking a look at it only now! 🙈

My new test was positive => parameters were produced: xc, yc, a, b, phi = Ellipse.params and even a > b that is nice. When will the new version be released?

We just released version 0.23.1, as you can see from PyPI or the release page of the repo.

Best,
Marianne

from scikit-image.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.