Commit 7bbda62b authored by Jiri (George) Lebl's avatar Jiri (George) Lebl Committed by George Lebl

add genius-graph.png to EXTRA_DIST


Sun Nov 11 00:14:04 2007  Jiri (George) Lebl <jirka@5z.com>

	* pixmaps/Makefile.am: add genius-graph.png to EXTRA_DIST

	* src/funclib.c: Implement DividePoly to divide polynomials
	  using long division.  This was one of those things that
	  I set aside to do "tommorrow" and it took close to a decade.

	* help/C/gel-function-list.xml: document DividePoly

	* configure.in: require GTK+ 2.4 (not 2.3.5 as previously)

	* NEWS: update


svn path=/trunk/; revision=601
parent d9a11c57
Sun Nov 11 00:14:04 2007 Jiri (George) Lebl <jirka@5z.com>
* pixmaps/Makefile.am: add genius-graph.png to EXTRA_DIST
* src/funclib.c: Implement DividePoly to divide polynomials
using long division. This was one of those things that
I set aside to do "tommorrow" and it took close to a decade.
* help/C/gel-function-list.xml: document DividePoly
* configure.in: require GTK+ 2.4 (not 2.3.5 as previously)
* NEWS: update
Sat Nov 10 16:58:14 2007 Jiri (George) Lebl <jirka@5z.com>
* src/gnome-genius.c: migrate to GtkFontButton and add website addy
......
......@@ -8,16 +8,18 @@ Changes to 1.0.1
causing the computer to grind to a halt.
* The .desktop file now has different Categories setup so will likely appear
in "Education" or "Accessories" menu rather than "Office"
* Add IsMatrixPositive, IsMatrixNonnegative, version, IsZero, IsIdentity,
DividePoly
* CHANGE: Remove IsGaussianInteger, we already have IsGaussInteger alias
IsComplexInteger
* Chop small numbers when they appear near other larger numbers. New
parameters OutputChopExponent and OutputChopWhenExponent
* Update the plotting widgetry from GtkExtra for prettier graphs
(Sebastian Dröge, me)
* Add IsMatrixPositive, IsMatrixNonnegative, version, IsZero, IsIdentity
* CHANGE: Remove IsGaussianInteger, we already have IsGaussInteger alias IsComplexInteger
* Add "Save all unsaved" menu item
* Add Ctrl->R for "Run"
* Default graphing limits are -10 to 10 for all axis (no more pi as default)
* Require at least GKT+ 2.3.5 for the GUI.
* Require at least GKT+ 2.4 for the GUI.
* Optionally compile with GtkSourceview2 and drop back to
GtkSourceview1 if unavailable (Sebastian Dröge)
* Fit dependent axis works for parametric plots
......
......@@ -16,7 +16,7 @@ VTE_REQUIRED=0.8.19
LIBGNOMEUI_REQUIRED=2.0.0
LIBGLADE_REQUIRED=1.99.2
LIBGNOME_REQUIRED=2.0.0
GTK_REQUIRED=2.3.5
GTK_REQUIRED=2.4.0
GLIB_REQUIRED=2.0.0
GTKSOURCEVIEW_REQUIRED=0.3.0
GTKSOURCEVIEW2_REQUIRED=2.0.2
......
......@@ -7,9 +7,6 @@
#include <glib-object.h>
G_BEGIN_DECLS
/* enumerations from "gtkiconlist.h" */
GType gtk_icon_list_mode_get_type (void);
#define GTK_TYPE_ICON_LIST_MODE (gtk_icon_list_mode_get_type())
/* enumerations from "gtkplot.h" */
GType gtk_plot_scale_get_type (void);
#define GTK_TYPE_PLOT_SCALE (gtk_plot_scale_get_type())
......@@ -43,9 +40,6 @@ GType gtk_plot_side_get_type (void);
/* enumerations from "gtkplotbar.h" */
GType gtk_plot_bar_units_get_type (void);
#define GTK_TYPE_PLOT_BAR_UNITS (gtk_plot_bar_units_get_type())
/* enumerations from "gtkplotcsurface.h" */
GType gtk_plot_projection_get_type (void);
#define GTK_TYPE_PLOT_PROJECTION (gtk_plot_projection_get_type())
/* enumerations from "gtkplotcanvas.h" */
GType gtk_plot_canvas_action_get_type (void);
#define GTK_TYPE_PLOT_CANVAS_ACTION (gtk_plot_canvas_action_get_type())
......@@ -57,6 +51,15 @@ GType gtk_plot_canvas_selection_mode_get_type (void);
#define GTK_TYPE_PLOT_CANVAS_SELECTION_MODE (gtk_plot_canvas_selection_mode_get_type())
GType gtk_plot_canvas_pos_get_type (void);
#define GTK_TYPE_PLOT_CANVAS_POS (gtk_plot_canvas_pos_get_type())
/* enumerations from "gtkplotcanvasline.h" */
GType gtk_plot_canvas_arrow_get_type (void);
#define GTK_TYPE_PLOT_CANVAS_ARROW (gtk_plot_canvas_arrow_get_type())
/* enumerations from "gtkplotcanvasplot.h" */
GType gtk_plot_canvas_plot_pos_get_type (void);
#define GTK_TYPE_PLOT_CANVAS_PLOT_POS (gtk_plot_canvas_plot_pos_get_type())
/* enumerations from "gtkplotcsurface.h" */
GType gtk_plot_projection_get_type (void);
#define GTK_TYPE_PLOT_PROJECTION (gtk_plot_projection_get_type())
/* enumerations from "gtkplotpc.h" */
GType gtk_plot_page_size_get_type (void);
#define GTK_TYPE_PLOT_PAGE_SIZE (gtk_plot_page_size_get_type())
......@@ -64,18 +67,6 @@ GType gtk_plot_page_orientation_get_type (void);
#define GTK_TYPE_PLOT_PAGE_ORIENTATION (gtk_plot_page_orientation_get_type())
GType gtk_plot_units_get_type (void);
#define GTK_TYPE_PLOT_UNITS (gtk_plot_units_get_type())
/* enumerations from "gtkplotsegment.h" */
GType gtk_plot_arrow_get_type (void);
#define GTK_TYPE_PLOT_ARROW (gtk_plot_arrow_get_type())
/* enumerations from "gtksheet.h" */
GType gtk_sheet_attr_type_get_type (void);
#define GTK_TYPE_SHEET_ATTR_TYPE (gtk_sheet_attr_type_get_type())
/* enumerations from "gtkplotcanvasline.h" */
GType gtk_plot_canvas_arrow_get_type (void);
#define GTK_TYPE_PLOT_CANVAS_ARROW (gtk_plot_canvas_arrow_get_type())
/* enumerations from "gtkplotcanvasplot.h" */
GType gtk_plot_canvas_plot_pos_get_type (void);
#define GTK_TYPE_PLOT_CANVAS_PLOT_POS (gtk_plot_canvas_plot_pos_get_type())
G_END_DECLS
#endif /* __GTKEXTRA_TYPE_BUILTINS_H__ */
......
......@@ -4302,6 +4302,22 @@ do (
</listitem>
</varlistentry>
<varlistentry id="gel-function-DividePoly">
<term>DividePoly</term>
<listitem>
<synopsis>DividePoly (p,q,&amp;r)</synopsis>
<para>Divide two polynomials (as vectors) using long division.
Returns the quotient
of the two polynomials. The optional argument <varname>r</varname>
is used to return the remainder. The remainder will have lower
degree than <varname>q</varname>.</para>
<para>
See
<ulink url="http://planetmath.org/encyclopedia/PolynomialLongDivision.html">Planetmath</ulink> for more information.
</para>
</listitem>
</varlistentry>
<varlistentry id="gel-function-IsPoly">
<term>IsPoly</term>
<listitem>
......
......@@ -4860,6 +4860,17 @@
Add two polynomials (vectors).
DividePoly
DividePoly (p,q,&r)
Divide two polynomials (as vectors) using long division. Returns
the quotient of the two polynomials. The optional argument r is
used to return the remainder. The remainder will have lower degree
than q.
See Planetmath for more information.
IsPoly
IsPoly (p)
......
......@@ -5,3 +5,5 @@ imagedir = \
$(datadir)/genius/
image_DATA = \
genius-graph.png
EXTRA_DIST = \
$(image_DATA)
......@@ -3665,14 +3665,31 @@ ExactDivision_op (GelCtx *ctx, GelETree * * a, gboolean *exception)
return gel_makenum (retw);
}
/* this can return 0! unlike what poly_cut_zeros does */
static int
poly_find_cutoff_size (GelMatrixW *m)
{
int i;
int cutoff;
for(i = gel_matrixw_width(m)-1; i >= 0; i--) {
GelETree *t = gel_matrixw_set_index(m,i,0);
if (t != NULL &&
! mpw_eql_ui(t->val.value, 0))
break;
}
cutoff = i+1;
return cutoff;
}
static void
poly_cut_zeros(GelMatrixW *m)
{
int i;
int cutoff;
for(i=gel_matrixw_width(m)-1;i>=1;i--) {
GelETree *t = gel_matrixw_index(m,i,0);
if ( ! mpw_eql_ui(t->val.value, 0))
GelETree *t = gel_matrixw_set_index(m,i,0);
if (t != NULL &&
! mpw_eql_ui(t->val.value, 0))
break;
}
cutoff = i+1;
......@@ -3849,48 +3866,119 @@ MultiplyPoly_op(GelCtx *ctx, GelETree * * a, gboolean *exception)
return n;
}
/*
static GelETree *
DividePoly_op(GelCtx *ctx, GelETree * * a, gboolean *exception)
{
GelETree *n;
long size;
int i,j;
GelETree *n, *rn, *ql;
long size, sizeq;
int i, j;
mpw_t accu;
GelMatrixW *m1,*m2,*mn;
GelEFunc *retmod = NULL;
GelMatrixW *pm, *qm, *mn, *rem;
GelEFunc *retrem = NULL;
mpw_t tmp;
if G_UNLIKELY ( ! check_poly (a, 2, "DividePoly", TRUE))
return NULL;
if (a[2] != NULL) {
retmod = get_reference (a[2], _("third argument"),
"DividePoly");
if G_UNLIKELY (retmod == NULL)
if (a[2]->type != NULL_NODE) {
retrem = get_reference (a[2], _("third argument"),
"DividePoly");
if G_UNLIKELY (retrem == NULL)
return NULL;
}
if G_UNLIKELY (a[3] != NULL) {
gel_errorout (_("%s: too many arguments"),
"DividePoly");
return NULL;
}
}
if G_UNLIKELY (a[3] != NULL) {
gel_errorout (_("%s: too many arguments"),
"DividePoly");
pm = a[0]->mat.matrix;
qm = a[1]->mat.matrix;
size = poly_find_cutoff_size (pm);
sizeq = poly_find_cutoff_size (qm);
if (sizeq <= 0) {
gel_errorout (_("%s: %s"),
"DividePoly",
_("Division by zero!"));
return NULL;
}
m1 = a[0]->mat.matrix;
m2 = a[1]->mat.matrix;
GET_NEW_NODE (n);
n->type = MATRIX_NODE;
n->mat.matrix = mn = gel_matrixw_new ();
n->mat.quoted = FALSE;
size = gel_matrixw_width (m1);
/* nothing to do */
if (size < sizeq) {
gel_matrixw_set_size (mn, 1, 1);
if (retrem != NULL) {
GET_NEW_NODE(rn);
rn->type = MATRIX_NODE;
rn->mat.matrix = gel_matrixw_copy (pm);
poly_cut_zeros (rn->mat.matrix);
rn->mat.quoted = FALSE;
d_set_value (retrem, rn);
}
return n;
}
gel_matrixw_set_size (mn, size, 1);
FIXME: implement long div
poly_cut_zeros(mn);
rem = gel_matrixw_copy (pm);
gel_matrixw_make_private (rem);
/* we know ql can't be zero */
ql = gel_matrixw_index (qm, sizeq-1, 0);
mpw_init (tmp);
for (i = size-sizeq; i >= 0; i--) {
GelETree *pt;
pt = gel_matrixw_set_index (rem, i+sizeq-1, 0);
if (pt == NULL || mpw_eql_ui (pt->val.value, 0)) {
/* Leave mn[i,0] at NULL (zero) */
continue;
}
gel_matrixw_set_index (mn, i, 0) = pt;
gel_matrixw_set_index (rem, i+sizeq-1, 0) = NULL;
mpw_div (pt->val.value,
pt->val.value, ql->val.value);
for (j = 0; j < sizeq-1; j++) {
GelETree *rv, *qt;
rv = gel_matrixw_set_index (rem, i+j, 0);
if (rv == NULL)
rv = gel_matrixw_set_index (rem, i+j, 0)
= gel_makenum_ui (0);
qt = gel_matrixw_index (qm, j, 0);
mpw_mul (tmp, pt->val.value, qt->val.value);
mpw_sub (rv->val.value, rv->val.value, tmp);
}
}
mpw_clear (tmp);
poly_cut_zeros (mn);
if (retrem != NULL) {
poly_cut_zeros (rem);
GET_NEW_NODE (rn);
rn->type = MATRIX_NODE;
rn->mat.matrix = rem;
rn->mat.quoted = FALSE;
d_set_value (retrem, rn);
} else {
gel_matrixw_free (rem);
}
return n;
}
*/
static GelETree *
PolyDerivative_op(GelCtx *ctx, GelETree * * a, gboolean *exception)
......@@ -5674,6 +5762,7 @@ gel_funclib_addall(void)
FUNC (AddPoly, 2, "p1,p2", "polynomial", N_("Add two polynomials (vectors)"));
FUNC (SubtractPoly, 2, "p1,p2", "polynomial", N_("Subtract two polynomials (as vectors)"));
FUNC (MultiplyPoly, 2, "p1,p2", "polynomial", N_("Multiply two polynomials (as vectors)"));
VFUNC (DividePoly, 3, "p,q,r", "polynomial", N_("Divide polynomial p by q, return the remainder in r"));
FUNC (PolyDerivative, 1, "p", "polynomial", N_("Take polynomial (as vector) derivative"));
FUNC (Poly2ndDerivative, 1, "p", "polynomial", N_("Take second polynomial (as vector) derivative"));
FUNC (TrimPoly, 1, "p", "polynomial", N_("Trim zeros from a polynomial (as vector)"));
......
......@@ -824,4 +824,12 @@ IsMatrixNonnegative(-ones(5,5)) false
[1e-50,1i] [0.0,1i]
[1e-50,1.0i] [0.0,1i]
[1e-50,1e-40i] [1e-50,1e-40i]
DividePoly([1,2],[0]) DividePoly([1,2],[0])
DividePoly([1,2],[1]) [1,2]
DividePoly([3,2],[1,1]) [2]
DividePoly([3,2],[1,1],&r);r [1]
DividePoly([1,2],[1,2,3]) [0]
DividePoly([1,2],[1,2,3],&r);r [1,2]
DividePoly([1,2,3],[1,2,3]) [1]
DividePoly([1,2,3],[1,2,3],&r);r [0]
load "longtest.gel" true
......@@ -131,6 +131,23 @@ function nthroottest() = (
true
);
function polydivtest() = (
for n=1 to 500 do (
sz = randint (20)+5;
p=randint(20,sz)-10;
sz = randint (15)+5;
do (
q=randint(20,sz)-10
) while IsZero(q);
d = DividePoly(p,q,&r);
if not AddPoly(MultiplyPoly(d,q),r) == TrimPoly (p) then (
error ("Error on Dividepoly p: " + p + " q: " + q);
return false
)
);
true
);
function LongTest() = (
errors = 0;
......@@ -163,6 +180,9 @@ function LongTest() = (
if not roottestquart() then (error("error on root test quartic");errors = errors + 1);
if not nthroottest() then (error("error on nth root test");errors = errors + 1);
# polynomial division
if not polydivtest() then (error("error on poly div test");errors = errors + 1);
# We print instead of return since we normally use load to run this
# and load doesn't output the return value
if errors > 0 then
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment