source: git/Singular/LIB/moddiq.lib @ 22c5aa

spielwiese
Last change on this file since 22c5aa was 22c5aa, checked in by Hans Schoenemann <hannes@…>, 4 years ago
moddiq.lib": shorter examples
  • Property mode set to 100644
File size: 9.1 KB
Line 
1///////////////////////////////////////////////////////////////////////////////
2version="version moddiq.lib 4.1.2.0 Feb_2020 "; // $Id$
3category="Commutative Algebra";
4info="
5LIBRARY:  moddiq.lib       Double ideal quotient using modular methods
6
7AUTHORS:  Y. Ishihara     yishihara@rikkyo.ac.jp
8
9OVERVIEW:
10  A library for computing ideal quotient and saturation in the polynomial ring
11  over the rational numbers using modular methods.
12
13REFERENCES:
14  M. Noro, K. Yokoyama: Usage of Modular Techniques for Efficient Computation of Ideal Operations.
15  Math.Comput.Sci. 12: 1, 1-32. (2017).
16
17PROCEDURES:
18  modQuotient(I,J); standard basis of (I:J) using modular methods
19  modSat(I,J); standard basis of (I:J^\infty) using modular methods
20";
21//UPCOMING PROCEDURES:
22//  moddiq(I,J); standard basis of (I:(I:J)) using modular methods
23//  modAssCheck(I,P); check if P is associated of I or not using modular methods
24//  IntermediatePrimaryDecomposition(I); compute intermediate primary decomposition of I
25//                                       by using modular method
26
27LIB "poly.lib";
28LIB "elim.lib";
29LIB "modular.lib";
30LIB "modstd.lib";
31
32proc modQuotient(def I, def J)
33"USAGE:   modQuotient(I,J); I,J ideal
34RETURN:   a standard basis of (I:J)
35NOTE:     The procedure computes a standard basis of (I:J) (over the rational
36          numbers) by using modular methods.
37SEE ALSO: modular; quotient
38EXAMPLE:  example modQuotient; shows an example"
39{
40    I = modStd(I);
41    def IJ=modular("quotient",list(I,J),primeTest_quotient,
42      Modstd::deleteUnluckyPrimes_std,pTest_quotient,finalTest_quotient);
43    return(IJ);
44}
45example
46{
47    "EXAMPLE:";
48    echo=2;
49    ring r=0,x(1..6),dp;
50    ideal i=cyclic(6);
51    ideal j=-15*var(5)+16*var(6)^3-60*var(6)^2+225*var(6)-4,2*var(5)^2-7*var(5)+2*var(6)^2-7*var(6)+28,(4*var(6)-1)*var(5)-var(6)+4,4*var(1)+var(5)+var(6),4*var(2)+var(5)+var(6),4*var(3)+var(5)+var(6),4*var(4)+var(5)+var(6);
52    modQuotient(i,modQuotient(i,j));
53    ideal id2=x(1)^2+x(1)*x(2)*x(3),x(2)^2-x(3)^3*x(2),x(3)^3+x(2)^5*x(1)*x(3);
54    quotient(id2,maxideal(3));
55}
56
57/* test if a prime number p is permissible for an ideal I
58 * i.e. it does not divide the denominator of any of the coeffients
59 * or numerator of any of the leading coefficients */
60static proc isPermissible(int p,ideal I)
61{
62    /* erase zero generators */
63    def J = simplify(I, 2);
64
65    /* clear denominators and compute the leading coeffients of
66       the cleared one and the original one*/
67    int n = ncols(J);
68    int i;
69    ideal K;
70    for(i = n; i > 0; i--)
71    {
72        K[i] = leadcoef(cleardenom(J[i]))*var(1)+leadcoef(J[i]);
73    }
74
75    /* change to characteristic p */
76    def br = basering;
77    list lbr = ringlist(br);
78    if (typeof(lbr[1]) == "int") { lbr[1] = p; }
79    else { lbr[1][1] = p; }
80    def rp = ring(lbr);
81    setring(rp);
82    ideal Kp = fetch(br, K);
83
84    /* test if any leading coefficient is missing */
85    if (intvec(size(Kp[1..n])) != 2:n) { setring(br); return(0); }
86    setring(br);
87    return(1);
88}
89
90/* test if the prime p is permissible for I and J */
91static proc primeTest_quotient(int p, alias list args)
92{
93    def I = args[1];
94    def J = args[2];
95    if(!isPermissible(p,I)){print("not permissible");return(0);}
96    if(!isPermissible(p,J)){print("not permissible");return(0);}
97    return(1);
98}
99
100/* test if 'command' applied to 'args' in characteristic p is the same as
101   'result' mapped to characteristic p */
102static proc pTest_quotient(string command, alias list args, alias def result,
103    int p)
104{
105    /* change to characteristic p */
106    def br = basering;
107    list lbr = ringlist(br);
108    if (typeof(lbr[1]) == "int") { lbr[1] = p; }
109    else { lbr[1][1] = p; }
110    def rp = ring(lbr);
111    setring(rp);
112    list args_fetched = fetch(br, args);
113    def Ip = args_fetched[1];
114    def Jp = args_fetched[2];
115    def Gp = fetch(br, result);
116    def IJp;
117    attrib(Ip, "isSB", 1);
118    attrib(Gp, "isSB", 1);
119
120    /* test if (Ip:Jp) is in Gp */
121    /* compute command(args) */
122    execute("IJp = "+command+"(Ip,Jp);");
123    int i;
124    for (i = ncols(IJp); i > 0; i--)
125    {
126        if (reduce(IJp[i], Gp, 1) != 0)
127        {
128            setring(br);
129            return(0);
130        }
131    }
132   
133    /* test if Gp is in (Ip:Jp) */
134    ideal GpJp=Gp*Jp;
135    for (i = ncols(GpJp); i > 0; i--)
136    {
137        if (reduce(GpJp[i], Ip, 1) != 0) { setring(br); return(0); }
138    }
139    setring(br);
140    return(1);
141}
142
143/* test if 'result' is a GB of (I:J) */
144static proc finalTest_quotient(string command, alias list args, def result)
145{
146    /* test if result is in (I:J)*/
147    attrib(result, "isSB", 1);
148    int i;
149    def IJ=result*args[2];
150    for (i = ncols(IJ); i > 0; i--)
151    {
152        if (reduce(IJ[i], args[1], 1) != 0) {print("fail") return(0); }
153    }
154    return(1);
155}
156
157proc modSat(def I, def J)
158"USAGE:   modSat(I,J); I,J ideal
159RETURN:   a standard basis of (I:J^\infty)
160NOTE:     The procedure computes a standard basis of (I:J^\infty) (over the rational
161          numbers) by using modular methods.
162KEYWORDS: saturation
163SEE ALSO: modular; sat
164EXAMPLE:  example modSat; shows an example"
165{
166    I = modStd(I);
167    def IJ=modular("sat",list(I,J),primeTest_sat,
168      deleteUnluckyPrimes_sat,pTest_sat,finalTest_sat);
169    return(IJ);
170}
171example
172{
173    "EXAMPLE:";
174    echo=2;
175    ring r=0,x(1..6),dp;
176    ideal i=cyclic(6);
177    ideal j=-15*var(5)+16*var(6)^3-60*var(6)^2+225*var(6)-4,2*var(5)^2-7*var(5)+2*var(6)^2-7*var(6)+28,(4*var(6)-1)*var(5)-var(6)+4,4*var(1)+var(5)+var(6),4*var(2)+var(5)+var(6),4*var(3)+var(5)+var(6),4*var(4)+var(5)+var(6);
178    modSat(i,modSat(i,j)[1])[1];
179    poly F     = x(1)^5+x(2)^5+(x(1)-x(2))^2*x(1)*x(2)*x(3);
180    ideal J    = jacob(F);
181    modSat(J,maxideal(1));
182}
183
184/* test if the prime p is permissible for I and J */
185static proc primeTest_sat(int p, alias list args)
186{
187    return(primeTest_quotient(p,args));
188}
189
190/* find entries in modresults which come from unlucky primes.
191 * For this, sort the entries into categories depending on their leading
192 * ideal and return the indices in all but the biggest category.
193 * Referring to Modstd::deleteUnlickyPrimes_std. */
194static proc deleteUnluckyPrimes_sat(alias list modresults)
195{
196    int size_modresults = size(modresults);
197
198    /* sort results into categories.
199     * each category is represented by three entries:
200     * - the corresponding leading ideal
201     * - the number of elements
202     * - the indices of the elements
203     */
204    list cat;
205    int size_cat;
206    def L=modresults[1][1]; // dummy assign to get the type of L
207    int i;
208    int j;
209    for (i = 1; i <= size_modresults; i++)
210    {
211        L = lead(modresults[i][1]);
212        attrib(L, "isSB", 1);
213        for (j = 1; j <= size_cat; j++)
214        {
215            if (size(L) == size(cat[j][1]))
216            {
217            if (size(reduce(L, cat[j][1], 5)) == 0)
218            {
219            if (size(reduce(cat[j][1], L, 5)) == 0)
220            {
221                cat[j][2] = cat[j][2]+1;
222                cat[j][3][cat[j][2]] = i;
223                break;
224            }
225            }
226            }
227        }
228        if (j > size_cat)
229        {
230            size_cat++;
231            cat[size_cat] = list();
232            cat[size_cat][1] = L;
233            cat[size_cat][2] = 1;
234            cat[size_cat][3] = list(i);
235        }
236    }
237
238    /* find the biggest categories */
239    int cat_max = 1;
240    int max = cat[1][2];
241    for (i = 2; i <= size_cat; i++)
242    {
243        if (cat[i][2] > max)
244        {
245            cat_max = i;
246            max = cat[i][2];
247        }
248    }
249
250    /* return all other indices */
251    list unluckyIndices;
252    for (i = 1; i <= size_cat; i++)
253    {
254        if (i != cat_max) { unluckyIndices = unluckyIndices + cat[i][3]; }
255    }
256    return(unluckyIndices);
257}
258
259/* test if 'command' applied to 'args' in characteristic p is the same as
260   'result' mapped to characteristic p */
261static proc pTest_sat(string command, alias list args, alias def result,
262    int p)
263{
264    /* change to characteristic p */
265    def br = basering;
266    list lbr = ringlist(br);
267    if (typeof(lbr[1]) == "int") { lbr[1] = p; }
268    else { lbr[1][1] = p; }
269    def rp = ring(lbr);
270    setring(rp);
271    list args_fetched = fetch(br, args);
272    def Ip = args_fetched[1];
273    def Jp = args_fetched[2];
274    def pResult = fetch(br, result);
275    def Gp=pResult[1];
276    def IJp;
277    attrib(Ip, "isSB", 1);
278    attrib(Gp, "isSB", 1);
279
280    /* test if (Ip:Jp^\infty) is in Gp */
281    /* compute command(args) */
282    execute("IJp = "+command+"(Ip,Jp)[1];");
283    int i;
284    for (i = ncols(IJp); i > 0; i--)
285    {
286        if (reduce(IJp[i], Gp, 1) != 0)
287        {
288            setring(br);
289            return(0);
290        }
291    }
292   
293    /* test if Gp is in (Ip:Jp^\infty) */
294    for (i = ncols(Gp); i > 0; i--)
295    {
296        if (reduce(Gp[i], IJp, 1) != 0) { setring(br); return(0); }
297    }
298    setring(br);
299    return(1);
300}
301
302/* test if 'result' is a GB of (I:J^\infty) */
303static proc finalTest_sat(string command, alias list args, def result)
304{
305    /* test if result is in (I:J^\infty)*/
306    int i;
307    ideal H = result[1];
308    int m=0;
309    for (i = 0 ; i < result[2]; i++){m++;}
310    ideal JGm;
311    for (i = 0 ; i < size(args[2]); i++)
312    {
313      JGm = JGm + args[2]^m;
314    }
315    def K=H*JGm;
316    for (i = ncols(K); i > 0; i--)
317    {
318        if (reduce(K[i], args[1], 1) != 0) {print("fail") return(0); }
319    }
320    return(1);
321}
322
323
Note: See TracBrowser for help on using the repository browser.