source: git/Singular/ideals.cc @ 64d729

spielwiese
Last change on this file since 64d729 was b982ef, checked in by Thomas Siebert <siebert@…>, 25 years ago
neue Variante von lift fuer non-stb in ideals Speicherfreigabe in ipconv und syz1 git-svn-id: file:///usr/local/Singular/svn/trunk@2673 2c84dea3-7e68-4137-9b89-c4e89433aadc
  • Property mode set to 100644
File size: 66.6 KB
Line 
1/****************************************
2*  Computer Algebra System SINGULAR     *
3****************************************/
4/* $Id: ideals.cc,v 1.41 1998-11-12 14:44:34 siebert Exp $ */
5/*
6* ABSTRACT - all basic methods to manipulate ideals
7*/
8
9/* includes */
10#include "mod2.h"
11#include "tok.h"
12#include "mmemory.h"
13#include "febase.h"
14#include "numbers.h"
15#include "polys.h"
16#include "ipid.h"
17#include "ring.h"
18#include "kstd1.h"
19#include "matpol.h"
20#include "weight.h"
21#include "intvec.h"
22#include "syz.h"
23#include "ideals.h"
24#include "lists.h"
25
26
27// #define WITH_OLD_MINOR
28
29static poly * idpower;
30/*collects the monomials in makemonoms, must be allocated befor*/
31static int idpowerpoint;
32/*index of the actual monomial in idpower*/
33static poly * givenideal;
34/*the ideal from which a power is computed*/
35
36/*0 implementation*/
37
38/*2
39* initialise an ideal
40*/
41#ifdef PDEBUG
42ideal idDBInit(int idsize, int rank, char *f, int l)
43#else
44ideal idInit(int idsize, int rank)
45#endif
46{
47  /*- initialise an ideal -*/
48#if defined(MDEBUG) && defined(PDEBUG)
49  ideal hh = (ideal )mmDBAllocBlock(sizeof(*hh),f,l);
50#else
51  ideal hh = (ideal )Alloc(sizeof(*hh));
52#endif
53  hh->nrows = 1;
54  hh->rank = rank;
55  IDELEMS(hh) = idsize;
56  if (idsize>0)
57  {
58#if defined(MDEBUG) && defined(PDEBUG)
59    hh->m = (poly *)mmDBAllocBlock0(idsize*sizeof(poly),f,l);
60#else
61    hh->m = (poly *)Alloc0(idsize*sizeof(poly));
62#endif
63  }
64  else
65    hh->m=NULL;
66  return hh;
67}
68
69void idPrint(ideal id)
70{
71  Print("Module of rank %d,real rank %d and %d generators.\n",
72         id->rank,idRankFreeModule(id),IDELEMS(id));
73  for (int i=0;i<IDELEMS(id);i++)
74  {
75    if (id->m[i]!=NULL)
76    {
77      Print("generator %d: ",i);pWrite(id->m[i]);
78    }
79  }
80}
81
82/*2
83* initialise the maximal ideal (at 0)
84*/
85ideal idMaxIdeal (void)
86{
87  int l;
88  ideal hh=NULL;
89
90  hh=idInit(pVariables,1);
91  for (l=0; l<pVariables; l++)
92  {
93    hh->m[l] = pOne();
94    pSetExp(hh->m[l],l+1,1);
95    pSetm(hh->m[l]);
96  }
97  return hh;
98}
99
100/*2
101* deletes an ideal/matrix
102*/
103#ifdef PDEBUG
104void idDBDelete (ideal* h, char *f, int l)
105#else
106void idDelete (ideal * h)
107#endif
108{
109  int j,elems;
110  if (*h == NULL)
111    return;
112  elems=j=(*h)->nrows*(*h)->ncols;
113  if (j>0)
114  {
115    do
116    {
117      #ifdef PDEBUG
118      pDBDelete(&((*h)->m[--j]),f,l);
119      #else
120      pDelete(&((*h)->m[--j]));
121      #endif
122    }
123    while (j>0);
124    #if defined(MDEBUG) && defined(PDEBUG)
125    mmDBFreeBlock((ADDRESS)((*h)->m),sizeof(poly)*elems,f,l);
126    #else
127    Free((ADDRESS)((*h)->m),sizeof(poly)*elems);
128    #endif
129  }
130  #if defined(MDEBUG) && defined(PDEBUG)
131  mmDBFreeBlock((ADDRESS)(*h),sizeof(**h),f,l);
132  #else
133  Free((ADDRESS)*h,sizeof(**h));
134  #endif
135  *h=NULL;
136}
137
138/*2
139*gives an ideal the minimal possible size
140*/
141void idSkipZeroes (ideal ide)
142{
143  int k;
144  int j = -1;
145  BOOLEAN change=FALSE;
146  for (k=0; k<IDELEMS(ide); k++)
147  {
148    if (ide->m[k] != NULL)
149    {
150      j++;
151      if (change)
152      {
153        ide->m[j] = ide->m[k];
154      }
155    }
156    else
157    {
158      change=TRUE;
159    }
160  }
161  if (change)
162  {
163    if (j == -1)
164      j = 0;
165    else
166    {
167      for (k=j+1; k<IDELEMS(ide); k++)
168        ide->m[k] = NULL;
169    }
170    pEnlargeSet(&(ide->m),IDELEMS(ide),j+1-IDELEMS(ide));
171    IDELEMS(ide) = j+1;
172  }
173}
174
175/*2
176* ideal id = (id[i])
177* result is leadcoeff(id[i]) = 1
178*/
179void idNorm(ideal id)
180{
181  for (int i=0; i<IDELEMS(id); i++)
182  {
183    if (id->m[i] != NULL)
184    {
185      pNorm(id->m[i]);
186    }
187  }
188}
189
190/*2
191* ideal id = (id[i]), c any number
192* if id[i] = c*id[j] then id[j] is deleted for j > i
193*/
194void idDelMultiples(ideal id)
195{
196  int i, j, t;
197  int k = IDELEMS(id), l = k;
198  for (i=k-2; i>=0; i--)
199  {
200    if (id->m[i]!=NULL)
201    {
202      for (j=l-1; j>i; j--)
203      {
204        if ((id->m[j]!=NULL)
205        && (pComparePolys(id->m[i], id->m[j])))
206        {
207          pDelete(&id->m[j]);
208          l--;
209          for(t=j; t<l; t++)
210          {
211            id->m[t] = id->m[t+1];
212          }
213        }
214      }
215    }
216  }
217  if (l != k)
218  {
219    pEnlargeSet(&id->m, k, l-k);
220    IDELEMS(id) = l;
221  }
222}
223
224/*2
225* ideal id = (id[i])
226* if id[i] = id[j] then id[j] is deleted for j > i
227*/
228void idDelEquals(ideal id)
229{
230  int i, j, t;
231  int k = IDELEMS(id), l = k;
232  for (i=k-2; i>=0; i--)
233  {
234    for (j=l-1; j>i; j--)
235    {
236      if (pEqualPolys(id->m[i], id->m[j]))
237      {
238        pDelete(&id->m[j]);
239        l--;
240        for(t=j; t<l; t++)
241        {
242          id->m[t] = id->m[t+1];
243        }
244      }
245    }
246  }
247  if (l != k)
248  {
249    pEnlargeSet(&id->m, k, l-k);
250    IDELEMS(id) = l;
251  }
252}
253
254//
255// Delete id[j], if Lm(j) == Lm(i) and j > i
256//
257void idDelLmEquals(ideal id)
258{
259  int i, j, t;
260  int k = IDELEMS(id), l = k;
261  for (i=k-2; i>=0; i--)
262  {
263    for (j=l-1; j>i; j--)
264    {
265      if (pLmEqual(id->m[i], id->m[j]))
266      {
267        pDelete(&id->m[j]);
268        l--;
269        for(t=j; t<l; t++)
270        {
271          id->m[t] = id->m[t+1];
272        }
273      }
274    }
275  }
276  if (l != k)
277  {
278    pEnlargeSet(&id->m, k, l-k);
279    IDELEMS(id) = l;
280  }
281}
282
283void idDelDiv(ideal id)
284{
285  int i, j, t;
286  int k = IDELEMS(id), l = k;
287  for (i=k-2; i>=0; i--)
288  {
289    for (j=l-1; j>i; j--)
290    {
291
292      if (((id->m[j] != NULL) && pDivisibleBy(id->m[i], id->m[j])) ||
293          (id->m[i] == NULL && id->m[j] == NULL))
294      {
295        pDelete(&id->m[j]);
296        l--;
297        for(t=j; t<l; t++)
298        {
299          id->m[t] = id->m[t+1];
300        }
301      }
302    }
303  }
304  if (l != k)
305  {
306    pEnlargeSet(&id->m, k, l-k);
307    IDELEMS(id) = l;
308  }
309}
310
311
312/*2
313* copy an ideal
314*/
315#ifdef PDEBUG
316ideal idDBCopy(ideal h1,char *f,int l)
317#else
318ideal idCopy (ideal h1)
319#endif
320{
321  int i;
322  ideal h2;
323
324//#ifdef TEST
325  if (h1 == NULL)
326  {
327#ifdef PDEBUG
328    h2=idDBInit(1,1,f,l);
329#else
330    h2=idInit(1,1);
331#endif
332  }
333  else
334//#endif
335  {
336#ifdef PDEBUG
337    h2=idDBInit(IDELEMS(h1),h1->rank,f,l);
338#else
339    h2=idInit(IDELEMS(h1),h1->rank);
340#endif
341    for (i=IDELEMS(h1)-1; i>=0; i--)
342#ifdef PDEBUG
343      h2->m[i] = pDBCopy(h1->m[i],f,l);
344#else
345      h2->m[i] = pCopy(h1->m[i]);
346#endif
347  }
348  return h2;
349}
350
351#ifdef PDEBUG
352void idDBTest(ideal h1,char *f,int l)
353{
354  int i;
355
356  if (h1 != NULL)
357  {
358    #ifdef MDEBUG
359    mmDBTestBlock(h1,sizeof(*h1),f,l);
360    #endif
361    /* to be able to test matrices: */
362    for (i=(IDELEMS(h1)*h1->nrows)-1; i>=0; i--)
363      pDBTest(h1->m[i],f,l);
364  }
365}
366#endif
367
368/*3
369* for idSort: compare a and b revlex inclusive module comp.
370*/
371static int pComp_RevLex(poly a, poly b)
372{
373 int l=pVariables;
374 while ((l>0) && (pGetExp(a,l)==pGetExp(b,l))) l--;
375 if (l==0)
376 {
377   if (pGetComp(a)==pGetComp(b)) return 0;
378   if (pGetComp(a)>pGetComp(b)) return 1;
379 }
380 else if (pGetExp(a,l)>pGetExp(b,l))
381   return 1;
382 return -1;
383}
384
385/*2
386*sorts the ideal w.r.t. the actual ringordering
387*uses lex-ordering when nolex = FALSE
388*/
389intvec *idSort(ideal id,BOOLEAN nolex)
390{
391  poly p,q;
392  intvec * result = new intvec(IDELEMS(id));
393  int i, j, actpos=0, newpos, l;
394  int diff, olddiff, lastcomp, newcomp;
395  BOOLEAN notFound;
396
397  pCompProc oldComp=pComp0;
398
399  if (!nolex) pComp0=pComp_RevLex;
400
401  for (i=0;i<IDELEMS(id);i++)
402  {
403    if (id->m[i]!=NULL)
404    {
405      notFound = TRUE;
406      newpos = actpos / 2;
407      diff = (actpos+1) / 2;
408      diff = (diff+1) / 2;
409      lastcomp = pComp0(id->m[i],id->m[(*result)[newpos]]);
410      if (lastcomp<0)
411      {
412        newpos -= diff;
413      }
414      else if (lastcomp>0)
415      {
416        newpos += diff;
417      }
418      else
419      {
420        notFound = FALSE;
421      }
422      while ((newpos>=0) && (newpos<actpos) && (notFound))
423      {
424        newcomp = pComp0(id->m[i],id->m[(*result)[newpos]]);
425        olddiff = diff;
426        if (diff>1)
427        {
428          diff = (diff+1) / 2;
429          if ((newcomp==1)
430          && (actpos-newpos>1)
431          && (diff>1)
432          && (newpos+diff>=actpos))
433          {
434            diff = actpos-newpos-1;
435          }
436          else if ((newcomp==-1)
437          && (diff>1)
438          && (newpos<diff))
439          {
440            diff = newpos;
441          }
442        }
443        if (newcomp<0)
444        {
445          if ((olddiff==1) && (lastcomp>0))
446            notFound = FALSE;
447          else
448            newpos -= diff;
449        }
450        else if (newcomp>0)
451        {
452          if ((olddiff==1) && (lastcomp<0))
453          {
454            notFound = FALSE;
455            newpos++;
456          }
457          else
458          {
459            newpos += diff;
460          }
461        }
462        else
463        {
464          notFound = FALSE;
465        }
466        lastcomp = newcomp;
467        if (diff==0) notFound=FALSE; /*hs*/
468      }
469      if (newpos<0) newpos = 0;
470      if (newpos>=actpos)
471      {
472        (*result)[actpos] = i;
473      }
474      else
475      {
476        for (j=actpos;j>newpos;j--)
477        {
478          (*result)[j] = (*result)[j-1];
479        }
480        (*result)[newpos] = i;
481      }
482      actpos++;
483    }
484  }
485  for (j=0;j<actpos;j++) (*result)[j]++;
486  pComp0=oldComp;
487  return result;
488}
489
490/*2
491* concat the lists h1 and h2 without zeros
492*/
493ideal idSimpleAdd (ideal h1,ideal h2)
494{
495  int i,j,r,l;
496  ideal result;
497
498  if (h1==NULL) return idCopy(h2);
499  if (h2==NULL) return idCopy(h1);
500  j = IDELEMS(h1)-1;
501  while ((j >= 0) && (h1->m[j] == NULL)) j--;
502  i = IDELEMS(h2)-1;
503  while ((i >= 0) && (h2->m[i] == NULL)) i--;
504  r = max(h1->rank,h2->rank);
505  if (i+j==(-2))
506    return idInit(1,r);
507  else
508    result=idInit(i+j+2,r);
509  for (l=j; l>=0; l--)
510  {
511    result->m[l] = pCopy(h1->m[l]);
512  }
513  r = i+j+1;
514  for (l=i; l>=0; l--, r--)
515  {
516    result->m[r] = pCopy(h2->m[l]);
517  }
518  return result;
519}
520
521/*2
522* h1 + h2
523*/
524ideal idAdd (ideal h1,ideal h2)
525{
526  ideal result = idSimpleAdd(h1,h2);
527  ideal tmp = idCompactify(result);
528
529  idDelete(&result);
530  return tmp;
531}
532
533/*2
534* h1 * h2
535*/
536ideal  idMult (ideal h1,ideal  h2)
537{
538  int i,j,k;
539  ideal  hh;
540
541  j = IDELEMS(h1);
542  while ((j > 0) && (h1->m[j-1] == NULL)) j--;
543  i = IDELEMS(h2);
544  while ((i > 0) && (h2->m[i-1] == NULL)) i--;
545  j = j * i;
546  if (j == 0)
547    hh = idInit(1,1);
548  else
549    hh=idInit(j,1);
550  if (h1->rank<h2->rank)
551    hh->rank = h2->rank;
552  else
553    hh->rank = h1->rank;
554  if (j==0) return hh;
555  k = 0;
556  for (i=0; i<IDELEMS(h1); i++)
557  {
558    if (h1->m[i] != NULL)
559    {
560      for (j=0; j<IDELEMS(h2); j++)
561      {
562        if (h2->m[j] != NULL)
563        {
564          hh->m[k] = pMult(pCopy(h1->m[i]),pCopy(h2->m[j]));
565          k++;
566        }
567      }
568    }
569  }
570  {
571    ideal tmp = idCompactify(hh);
572    idDelete(&hh);
573    return tmp;
574    //return hh;
575  }
576}
577
578/*2
579*returns true if h is the zero ideal
580*/
581BOOLEAN idIs0 (ideal h)
582{
583  int i;
584
585  if (h == NULL) return TRUE;
586  i = IDELEMS(h);
587  while ((i > 0) && (h->m[i-1] == NULL))
588  {
589    i--;
590  }
591  if (i == 0)
592    return TRUE;
593  else
594    return FALSE;
595}
596
597/*2
598* return the maximal component number found in any polynomial in s
599*/
600int idRankFreeModule (ideal s)
601{
602  if (s!=NULL)
603  {
604    int  j=0;
605    int  l=IDELEMS(s);
606    poly *p=s->m;
607    int  k;
608
609    for (; l != 0; l--)
610    {
611      if (*p!=NULL)
612      {
613        k = pMaxComp(*p);
614        if (k>j) j = k;
615      }
616      p++;
617    }
618    return j;
619  }
620  return -1;
621}
622
623/*2
624*returns true if id is homogenous with respect to the aktual weights
625*/
626BOOLEAN idHomIdeal (ideal id, ideal Q)
627{
628  int i;
629  BOOLEAN     b;
630  if ((id == NULL) || (IDELEMS(id) == 0)) return TRUE;
631  i = 0;
632  b = TRUE;
633  while ((i < IDELEMS(id)) && b)
634  {
635    b = pIsHomogeneous(id->m[i]);
636    i++;
637  }
638  if ((b) && (Q!=NULL) && (IDELEMS(Q)>0))
639  {
640    i=0;
641    while ((i < IDELEMS(Q)) && b)
642    {
643      b = pIsHomogeneous(Q->m[i]);
644      i++;
645    }
646  }
647  return b;
648}
649
650/*2
651*returns a minimized set of generators of h1
652*/
653ideal idMinBase (ideal h1)
654{
655  ideal h2, h3,h4,e;
656  int j,k;
657  int i,l,ll;
658  intvec * wth;
659  BOOLEAN homog;
660
661  homog = idHomModule(h1,currQuotient,&wth);
662  if ((currRing->OrdSgn == 1) && (!homog))
663  {
664    Warn("minbase applies only to the local or homogeneous case");
665    e=idCopy(h1);
666    return e;
667  }
668  if ((currRing->OrdSgn == 1) && (homog))
669  {
670    lists re=min_std(h1,currQuotient,(tHomog)homog,&wth,NULL,0,3);
671    h2 = (ideal)re->m[1].data;
672    re->m[1].data = NULL;
673    re->m[1].rtyp = NONE;
674    re->Clean();
675    return h2;
676  }
677  e=idInit(1,h1->rank);
678  if (idIs0(h1))
679  {
680    return e;
681  }
682  pEnlargeSet(&(e->m),IDELEMS(e),15);
683  IDELEMS(e) = 16;
684  h2 = kStd(h1,currQuotient,isNotHomog,NULL);
685  h3 = idMaxIdeal();
686  h4=idMult(h2,h3);
687  idDelete(&h3);
688  h3=kStd(h4,currQuotient,isNotHomog,NULL);
689  k = IDELEMS(h3);
690  while ((k > 0) && (h3->m[k-1] == NULL)) k--;
691  j = -1;
692  l = IDELEMS(h2);
693  while ((l > 0) && (h2->m[l-1] == NULL)) l--;
694  for (i=l-1; i>=0; i--)
695  {
696    if (h2->m[i] != NULL)
697    {
698      ll = 0;
699      while ((ll < k) && ((h3->m[ll] == NULL)
700      || !pDivisibleBy(h3->m[ll],h2->m[i])))
701        ll++;
702      if (ll >= k)
703      {
704        j++;
705        if (j > IDELEMS(e)-1)
706        {
707          pEnlargeSet(&(e->m),IDELEMS(e),16);
708          IDELEMS(e) += 16;
709        }
710        e->m[j] = pCopy(h2->m[i]);
711      }
712    }
713  }
714  idDelete(&h2);
715  idDelete(&h3);
716  idDelete(&h4);
717  if (currQuotient!=NULL)
718  {
719    h3=idInit(1,e->rank);
720    h2=kNF(h3,currQuotient,e);
721    idDelete(&h3);
722    idDelete(&e);
723    e=h2;
724  }
725  idSkipZeroes(e);
726  return e;
727}
728
729/*2
730*the minimal index of used variables - 1
731*/
732int pLowVar (poly p)
733{
734  int k,l,lex;
735
736  if (p == NULL) return -1;
737
738  k = 32000;/*a very large dummy value*/
739  while (p != NULL)
740  {
741    l = 1;
742    lex = pGetExp(p,l);
743    while ((l <= pVariables) && (lex == 0))
744    {
745      l++;
746      lex = pGetExp(p,l);
747    }
748    l--;
749    if (l < k) k = l;
750    pIter(p);
751  }
752  return k;
753}
754
755/*3
756*multiplies p with t (!cas) or  (t-1)
757*the index of t is:1, so we have to shift all variables
758*p is NOT in the actual ring, it has no t
759*/
760static poly pMultWithT (poly p,BOOLEAN cas)
761{
762  /*qp is the working pointer in p*/
763  /*result is the result, qresult is the working pointer*/
764  /*pp is p in the actual ring(shifted), qpp the working pointer*/
765  poly result,qp,pp;
766  poly qresult=NULL;
767  poly qpp=NULL;
768  int  i,j,lex;
769  number n;
770
771  pp = NULL;
772  result = NULL;
773  qp = p;
774  while (qp != NULL)
775  {
776    i = 0;
777    if (result == NULL)
778    {/*first monomial*/
779      result = pInit();
780      qresult = result;
781    }
782    else
783    {
784      qresult->next = pInit();
785      pIter(qresult);
786    }
787    for (j=pVariables-1; j>0; j--)
788    {
789      lex = pGetExp(qp,j);
790      pSetExp(qresult,j+1,lex);/*copy all variables*/
791    }
792    lex = pGetComp(qp);
793    pSetComp(qresult,lex);
794    n=nCopy(pGetCoeff(qp));
795    pSetCoeff0(qresult,n);
796    qresult->next = NULL;
797    pSetm(qresult);
798    /*qresult is now qp brought into the actual ring*/
799    if (cas)
800    { /*case: mult with t-1*/
801      pSetExp(qresult,1,0);
802      pSetm(qresult);
803      if (pp == NULL)
804      { /*first monomial*/
805        pp = pCopy(qresult);
806        qpp = pp;
807      }
808      else
809      {
810        qpp->next = pCopy(qresult);
811        pIter(qpp);
812      }
813      pGetCoeff(qpp)=nNeg(pGetCoeff(qpp));
814      /*now qpp contains -1*qp*/
815    }
816    pSetExp(qresult,1,1);/*this is mult. by t*/
817    pSetm(qresult);
818    pIter(qp);
819  }
820  /*
821  *now p is processed:
822  *result contains t*p
823  * if cas: pp contains -1*p (in the new ring)
824  */
825  if (cas)  qresult->next = pp;
826  /*  else      qresult->next = NULL;*/
827  return result;
828}
829
830/*3
831*deletes the place of t in p (t: variable with index 1)
832*p is NOT in the actual ring: it has pVariables+1 variables
833*/
834static poly pDivByT (poly * p,int size)
835{
836
837  poly result=NULL,
838       resultp=NULL , /** working pointer in result **/
839       pp;
840  int  i,j;
841
842  while (*p != NULL)
843  {
844    i = 0;
845    if (result == NULL)
846    {/*the first monomial*/
847      result = pInit();
848      resultp = result;
849      resultp->next = NULL;
850    }
851    else
852    {
853      resultp->next = pInit();
854      pIter(resultp);
855      resultp->next = NULL;
856    }
857    for (j=1; j<=pVariables; j++)
858    {
859      pSetExp(resultp,j,pGetExp(*p,j+1));
860    }
861    pSetComp(resultp,pGetComp(*p));
862    pSetCoeff0(resultp,pGetCoeff(*p));
863    pSetm(resultp);
864    pp = (*p)->next;
865    Free((ADDRESS)*p,size);
866    *p = pp;
867  }
868  return result;
869}
870
871/*2
872*dehomogenized the generators of the ideal id1 with the leading
873*monomial of p replaced by n
874*/
875ideal idDehomogen (ideal id1,poly p,number n)
876{
877  int i;
878  ideal result;
879
880  if (idIs0(id1))
881  {
882    return idInit(1,id1->rank);
883  }
884  result=idInit(IDELEMS(id1),id1->rank);
885  for (i=0; i<IDELEMS(id1); i++)
886  {
887    result->m[i] = pDehomogen(id1->m[i],p,n);
888  }
889  return result;
890}
891
892/*2
893* verschiebt die Indizees der Modulerzeugenden um i
894*/
895void pShift (poly * p,int i)
896{
897  poly qp1 = *p,qp2 = *p;/*working pointers*/
898  int     j = pMaxComp(*p),k = pMinComp(*p);
899
900  if (j+i < 0) return ;
901  while (qp1 != NULL)
902  {
903    if ((pGetComp(qp1)+i > 0) || ((j == -i) && (j == k)))
904    {
905      pSetComp(qp1,pGetComp(qp1)+i);
906      qp2 = qp1;
907      pIter(qp1);
908    }
909    else
910    {
911      if (qp2 == *p)
912      {
913        pIter(*p);
914        qp2->next = NULL;
915        pDelete(&qp2);
916        qp2 = *p;
917        qp1 = *p;
918      }
919      else
920      {
921        qp2->next = qp1->next;
922        qp1->next = NULL;
923        pDelete(&qp1);
924        qp1 = qp2->next;
925      }
926    }
927  }
928}
929
930/*2
931*initialized a field with r numbers between beg and end for the
932*procedure idNextChoise
933*/
934void idInitChoise (int r,int beg,int end,BOOLEAN  *endch,int * choise)
935{
936  /*returns the first choise of r numbers between beg and end*/
937  int i;
938  for (i=0; i<r; i++)
939  {
940    choise[i] = 0;
941  }
942  if (r <= end-beg+1)
943    for (i=0; i<r; i++)
944    {
945      choise[i] = beg+i;
946    }
947  if (r > end-beg+1)
948    *endch = TRUE;
949  else
950    *endch = FALSE;
951}
952
953/*2
954*returns the next choise of r numbers between beg and end
955*/
956void idGetNextChoise (int r,int end,BOOLEAN  *endch,int * choise)
957{
958  int i = r-1,j;
959  while ((i >= 0) && (choise[i] == end))
960  {
961    i--;
962    end--;
963  }
964  if (i == -1)
965    *endch = TRUE;
966  else
967  {
968    choise[i]++;
969    for (j=i+1; j<r; j++)
970    {
971      choise[j] = choise[i]+j-i;
972    }
973    *endch = FALSE;
974  }
975}
976
977/*2
978*takes the field choise of d numbers between beg and end, cancels the t-th
979*entree and searches for the ordinal number of that d-1 dimensional field
980* w.r.t. the algorithm of construction
981*/
982int idGetNumberOfChoise(int t, int d, int begin, int end, int * choise)
983{
984  int * localchoise,i,result=0;
985  BOOLEAN b=FALSE;
986
987  if (d<=1) return 1;
988  localchoise=(int*)Alloc((d-1)*sizeof(int));
989  idInitChoise(d-1,begin,end,&b,localchoise);
990  while (!b)
991  {
992    result++;
993    i = 0;
994    while ((i<t) && (localchoise[i]==choise[i])) i++;
995    if (i>=t)
996    {
997      i = t+1;
998      while ((i<d) && (localchoise[i-1]==choise[i])) i++;
999      if (i>=d)
1000      {
1001        Free((ADDRESS)localchoise,(d-1)*sizeof(int));
1002        return result;
1003      }
1004    }
1005    idGetNextChoise(d-1,end,&b,localchoise);
1006  }
1007  Free((ADDRESS)localchoise,(d-1)*sizeof(int));
1008  return 0;
1009}
1010
1011/*2
1012*computes the binomial coefficient
1013*/
1014int binom (int n,int r)
1015{
1016  int i,result;
1017
1018  if (r==0) return 1;
1019  if (n-r<r) return binom(n,n-r);
1020  result = n-r+1;
1021  for (i=2;i<=r;i++)
1022  {
1023    result *= n-r+i;
1024    result /= i;
1025  }
1026  return result;
1027}
1028
1029/*2
1030*the free module of rank i
1031*/
1032ideal idFreeModule (int i)
1033{
1034  int j;
1035  ideal h;
1036
1037  h=idInit(i,i);
1038  for (j=0; j<i; j++)
1039  {
1040    h->m[j] = pOne();
1041    pSetComp(h->m[j],j+1);
1042  }
1043  return h;
1044}
1045
1046/*2
1047* h3 := h1 intersect h2
1048*/
1049ideal idSect (ideal h1,ideal h2)
1050{
1051  ideal first=h2,second=h1,temp,temp1,result;
1052  int i,j,k,flength,slength,length,rank=min(h1->rank,h2->rank);
1053  intvec *w;
1054  poly p,q;
1055
1056  if ((idIs0(h1)) && (idIs0(h2)))  return idInit(1,rank);
1057  if (IDELEMS(h1)<IDELEMS(h2))
1058  {
1059    first = h1;
1060    second = h2;
1061  }
1062  flength = idRankFreeModule(first);
1063  slength = idRankFreeModule(second);
1064  length  = max(flength,slength);
1065  if (length==0)
1066  {
1067    length = 1;
1068  }
1069  temp = idInit(IDELEMS(first),1);
1070  j = IDELEMS(temp);
1071  while ((j>0) && (first->m[j-1]==NULL)) j--;
1072  k = 0;
1073  for (i=0;i<j;i++)
1074  {
1075    if (first->m[i]!=NULL)
1076    {
1077      temp->m[k] = pCopy(first->m[i]);
1078      q = pOne();
1079      pSetComp(q,i+1+length);
1080      if (flength==0) pShift(&(temp->m[k]),1);
1081      p = temp->m[k];
1082      while (pNext(p)) pIter(p);
1083      pNext(p) = q;
1084      k++;
1085    }
1086  }
1087  pEnlargeSet(&(temp->m),IDELEMS(temp),j+IDELEMS(second)-IDELEMS(temp));
1088  IDELEMS(temp) = j+IDELEMS(second);
1089  for (i=0;i<IDELEMS(second);i++)
1090  {
1091    if (second->m[i]!=NULL)
1092    {
1093      temp->m[k] = pCopy(second->m[i]);
1094      if (slength==0) pShift(&(temp->m[k]),1);
1095      k++;
1096    }
1097  }
1098  pSetSyzComp(length);
1099  temp1 = kStd(temp,currQuotient,testHomog,&w,NULL,length);
1100  if (w!=NULL) delete w;
1101  pSetSyzComp(0);
1102  idDelete(&temp);
1103  result = idInit(IDELEMS(temp1),rank);
1104  j = 0;
1105  for (i=0;i<IDELEMS(temp1);i++)
1106  {
1107    if ((temp1->m[i]!=NULL)
1108    && (pGetComp(temp1->m[i])>length))
1109    {
1110      p = temp1->m[i];
1111//PrintS("die Syzygie ist: ");pWrite(p);
1112      temp1->m[i] = NULL;
1113      while (p!=NULL)
1114      {
1115        q = pNext(p);
1116        pNext(p) = NULL;
1117        k = pGetComp(p)-1-length;
1118        pSetComp(p,0);
1119//PrintS("das %d-te Element: ",k);pWrite(first->m[k]);
1120        result->m[j] = pAdd(result->m[j],pMult(pCopy(first->m[k]),p));
1121        p = q;
1122      }
1123//PrintS("Generator ist: ");pWrite(result->m[j]);
1124      j++;
1125    }
1126  }
1127  idSkipZeroes(result);
1128  return result;
1129}
1130
1131/*2
1132* ideal/module intersection for a list of objects
1133* given as 'resolvente'
1134*/
1135ideal idMultSect(resolvente arg, int length)
1136{
1137  int i,j=0,k=0,syzComp,l,maxrk=-1,realrki;
1138  ideal bigmat,tempstd,result;
1139  poly p;
1140  int isIdeal=0;
1141  intvec * w=NULL;
1142
1143  /* find 0-ideals and max rank -----------------------------------*/
1144  for (i=0;i<length;i++)
1145  {
1146    if (!idIs0(arg[i]))
1147    {
1148      realrki=idRankFreeModule(arg[i]);
1149      k++;
1150      j += IDELEMS(arg[i]);
1151      if (realrki>maxrk) maxrk = realrki;
1152    }
1153    else
1154    {
1155      if (arg[i]!=NULL)
1156      {
1157        return idInit(1,arg[i]->rank);
1158      }
1159    }
1160  }
1161  if (maxrk == 0)
1162  {
1163    isIdeal = 1;
1164    maxrk = 1;
1165  }
1166  /* init -----------------------------------------------------------*/
1167  j += maxrk;
1168  bigmat = idInit(j,(k+1)*maxrk);
1169  syzComp = k*maxrk;
1170  pSetSyzComp(syzComp);
1171  /* create unit matrices ------------------------------------------*/
1172  for (i=0;i<maxrk;i++)
1173  {
1174    for (j=0;j<=k;j++)
1175    {
1176      p = pOne();
1177      pSetComp(p,i+1+j*maxrk);
1178      pSetm(p);
1179      bigmat->m[i] = pAdd(bigmat->m[i],p);
1180    }
1181  }
1182  /* enter given ideals ------------------------------------------*/
1183  i = maxrk;
1184  k = 0;
1185  for (j=0;j<length;j++)
1186  {
1187    if (arg[j]!=NULL)
1188    {
1189      for (l=0;l<IDELEMS(arg[j]);l++)
1190      {
1191        if (arg[j]->m[l]!=NULL)
1192        {
1193          bigmat->m[i] = pCopy(arg[j]->m[l]);
1194          pShift(&(bigmat->m[i]),k*maxrk+isIdeal);
1195          i++;
1196        }
1197      }
1198      k++;
1199    }
1200  }
1201  /* std computation --------------------------------------------*/
1202  tempstd = kStd(bigmat,currQuotient,testHomog,&w,NULL,syzComp);
1203  if (w!=NULL) delete w;
1204  idDelete(&bigmat);
1205  pSetSyzComp(0);
1206  /* interprete result ----------------------------------------*/
1207  result = idInit(8,maxrk);
1208  k = 0;
1209  for (j=0;j<IDELEMS(tempstd);j++)
1210  {
1211    if ((tempstd->m[j]!=NULL) && (pGetComp(tempstd->m[j])>syzComp))
1212    {
1213      if (k>=IDELEMS(result))
1214      {
1215        pEnlargeSet(&(result->m),IDELEMS(result),8);
1216        IDELEMS(result) += 8;
1217      }
1218      p = tempstd->m[j];
1219      tempstd->m[j] = NULL;
1220      pShift(&p,-syzComp-isIdeal);
1221      result->m[k] = p;
1222      k++;
1223    }
1224  }
1225  /* clean up ----------------------------------------------------*/
1226  idDelete(&tempstd);
1227  idSkipZeroes(result);
1228  return result;
1229}
1230
1231/*2
1232*computes the rank of the free module in which h1 embeds
1233*/
1234int lengthFreeModule (ideal  h1)
1235{
1236  int     i,j,k;
1237
1238  if (idIs0(h1)) return 0;
1239  k = -1;
1240  for (i=0; i<IDELEMS(h1); i++)
1241  {
1242    j = pMaxComp(h1->m[i]);
1243    if (j>k) k = j;
1244  }
1245  return k;
1246}
1247
1248/*2
1249*computes syzygies of h1,
1250*if quot != NULL it computes in the quotient ring modulo "quot"
1251*/
1252ideal  idPrepare (ideal  h1,ideal  quot, tHomog h,
1253  int* syzcomp, int *quotgen, int *quotdim, intvec **w)
1254{
1255  ideal   h2, h3;
1256  int     i;
1257  int     j,jj=0,k;
1258  poly    p,q;
1259  BOOLEAN orderChanged=FALSE;
1260
1261  if (idIs0(h1)) return NULL;
1262  k = lengthFreeModule(h1);
1263  if (*syzcomp<k) *syzcomp = k;
1264  h2 = NULL;
1265  h2=idCopy(h1);
1266  i = IDELEMS(h2)-1;
1267  //while ((i >= 0) && (h2->m[i] == NULL)) i--;
1268  if (k == 0)
1269  {
1270    for (j=0; j<=i; j++) pShift(&(h2->m[j]),1);
1271    *syzcomp = 1;
1272  }
1273  h2->rank = *syzcomp+i+1;
1274  for (j=0; j<=i; j++)
1275  {
1276    p = h2->m[j];
1277    q = pOne();
1278#ifdef DRING
1279    if (pDRING) { pdSetDFlag(q,1); pSetm(q); }
1280#endif
1281    pSetComp(q,*syzcomp+1+j);
1282    if (p!=NULL)
1283    {
1284      while (pNext(p)) pIter(p);
1285      p->next = q;
1286    }
1287    else
1288      h2->m[j]=q;
1289  }
1290  if (currRing->order[0]!=ringorder_c)
1291  {
1292    while ((currRing->order[jj]!=0) && (currRing->order[jj]!=ringorder_c)
1293           && (currRing->order[jj]!=ringorder_C))
1294    {
1295      jj++;
1296    }
1297    if ((pOrdSgn==1) && (h==TRUE) && (*syzcomp==1) && (!pLexOrder)
1298        && (currRing->order[jj]==ringorder_c))
1299    {
1300      for(j=0;(j<IDELEMS(h2) && (!orderChanged));j++)
1301      {
1302        if (h2->m[j] != NULL)
1303        {
1304          p=h2->m[j];
1305          while ((p!=NULL)
1306          && (pGetComp(p)<=*syzcomp))
1307          {
1308            if (pIsConstantComp(p))
1309            {
1310              pSetSyzComp(*syzcomp);
1311              orderChanged=TRUE;
1312              break;
1313            }
1314            pIter(p);
1315          }
1316        }
1317      }
1318    }
1319    else
1320    {
1321      pSetSyzComp(*syzcomp);
1322      orderChanged=TRUE;
1323    }
1324  }
1325
1326//  if (orderChanged) PrintS("order changed\n");
1327//  else PrintS("order not changed\n");
1328#ifdef PDEBUG
1329  for(j=0;j<IDELEMS(h2);j++) pTest(h2->m[j]);
1330#endif
1331  h3=kStd(h2,quot,h,w,NULL,*syzcomp);
1332  //h3->rank = h2->rank; done by kStd -> initBuchMora -> initS
1333  h3->rank-=*syzcomp;
1334  idDelete(&h2);
1335  if (orderChanged) pSetSyzComp(0);
1336  return h3;
1337}
1338
1339ideal idSyzygies (ideal  h1,ideal  quot, tHomog h,intvec **w)
1340{
1341  int d;
1342  return idSyzygies(h1,quot,h,w,FALSE,d);
1343}
1344
1345ideal idSyzygies (ideal  h1,ideal  quot, tHomog h,intvec **w,
1346                  BOOLEAN setRegularity, int &deg)
1347{
1348  ideal e, h3;
1349  poly  p;
1350  int   i, j, k=0, quotdim, quotgen,length=0,reg;
1351  BOOLEAN isMonomial=TRUE;
1352
1353#ifdef PDEBUG
1354  int ii;
1355  for(ii=0;ii<IDELEMS(h1);ii++) pTest(h1->m[ii]);
1356  if (quot!=NULL)
1357  {
1358    for(ii=0;ii<IDELEMS(quot);ii++) pTest(quot->m[ii]);
1359  }
1360#endif
1361  if (idIs0(h1))
1362    return idFreeModule(IDELEMS(h1));
1363  h3=idPrepare(h1,quot,h,&k,&quotgen,&quotdim,w);
1364  if (h3==NULL)
1365    return idFreeModule(IDELEMS(h1));
1366  i = -1;
1367  e=idInit(16,h3->rank);
1368  for (j=0; j<IDELEMS(h3); j++)
1369  {
1370    if (h3->m[j] != NULL)
1371    {
1372      if (pMinComp(h3->m[j]) > k)
1373      {
1374        p = h3->m[j];
1375        h3->m[j]=NULL;
1376        pShift(&p,-k);
1377        if (p!=NULL)
1378        {
1379          i++;
1380          if (i+1 >= IDELEMS(e))
1381          {
1382            pEnlargeSet(&(e->m),IDELEMS(e),16);
1383            IDELEMS(e) += 16;
1384          }
1385          e->m[i] = p;
1386        }
1387      }
1388      else
1389      {
1390        isMonomial=isMonomial && (pNext(h3->m[j])==NULL);
1391        pDelete(&pNext(h3->m[j]));
1392      }
1393    }
1394  }
1395  if ((!isMonomial) && (!TEST_OPT_NOTREGULARITY) && (setRegularity) && (h==isHomog))
1396  {
1397    idSkipZeroes(h3);
1398    resolvente res = sySchreyerResolvente(h3,-1,&length,TRUE);
1399    intvec * dummy = syBetti(res,length,&reg, *w);
1400    deg = reg+2;
1401    delete dummy;
1402    for (j=0;j<length;j++)
1403    {
1404      if (res[j]!=NULL) idDelete(&(res[j]));
1405    }
1406    Free((ADDRESS)res,length*sizeof(ideal));
1407  }
1408  idDelete(&h3);
1409  idSkipZeroes(e);
1410  return e;
1411}
1412
1413/*2
1414* computes syzygies and minimizes the input (h1)
1415* ONLY used in syMinRes
1416*/
1417ideal idSyzMin (ideal h1,ideal  quot, tHomog h,intvec **w,
1418                  BOOLEAN setRegularity, int &deg)
1419{
1420  ideal e, h3;
1421  poly  p;
1422  intvec * reord;
1423  int   i, l=0, j, k=0, quotdim, quotgen,length=0,reg;
1424  BOOLEAN isMonomial=TRUE;
1425
1426  if (idIs0(h1))
1427    return idFreeModule(1);
1428//PrintS("h1 vorher\n");
1429//for (i=0;i<IDELEMS(h1);i++)
1430//{
1431//Print("Element %d: ",i);pWrite(h1->m[i]);
1432//}
1433  idSkipZeroes(h1);
1434  h3=idPrepare(h1,quot,h,&k,&quotgen,&quotdim,w);
1435//PrintS("h1 nachher\n");
1436//for (i=0;i<IDELEMS(h3);i++)
1437//{
1438//Print("Element %d: ",i);pWrite(h3->m[i]);
1439//}
1440  if (h3==NULL)
1441    return idFreeModule(1);
1442  for (i=IDELEMS(h1);i!=0;i--)
1443    pDelete(&(h1->m[i-1]));
1444  reord = new intvec(IDELEMS(h1)+1);
1445  i = -1;
1446  e=idInit(16,h3->rank);
1447  for (j=0; j<IDELEMS(h3); j++)
1448  {
1449    if (h3->m[j] != NULL)
1450    {
1451      p = h3->m[j];
1452      if (pGetComp(p) > k)
1453      {
1454        h3->m[j]=NULL;
1455        pShift(&p,-k);
1456        if (p!=NULL)
1457        {
1458          i++;
1459          if (i+1 >= IDELEMS(e))
1460          {
1461            pEnlargeSet(&(e->m),IDELEMS(e),16);
1462            IDELEMS(e) += 16;
1463          }
1464          e->m[i] = p;
1465        }
1466      }
1467      else
1468      {
1469        while ((pNext(p)!=NULL) && (pGetComp(pNext(p))<=k)) pIter(p);
1470        if (pIsConstantComp(pNext(p)))
1471        {
1472          (*reord)[pGetComp(pNext(p))-k] = l+1;
1473//Print("Element %d mit Comp %d: ",j,pGetComp(pNext(p))-k);
1474//pWrite(h3->m[j]);
1475          h1->m[l] = h3->m[j];
1476          h3->m[j] = pCopy(h1->m[l]);
1477          pDelete(&pNext(p));
1478          l++;
1479        }
1480        isMonomial=isMonomial && (pGetComp(pNext(h3->m[j]))>k);
1481        pDelete(&pNext(h3->m[j]));
1482      }
1483    }
1484  }
1485  if ((!isMonomial) && (!TEST_OPT_NOTREGULARITY) && (setRegularity) && (h==isHomog))
1486  {
1487    idSkipZeroes(h3);
1488    resolvente res = sySchreyerResolvente(h3,0,&length);
1489    intvec * dummy = syBetti(res,length,&reg, *w);
1490    deg = reg+2;
1491    delete dummy;
1492    for (j=0;j<length;j++)
1493    {
1494      if (res[j]!=NULL) idDelete(&(res[j]));
1495    }
1496    Free((ADDRESS)res,length*sizeof(ideal));
1497  }
1498  idDelete(&h3);
1499//PrintS("Komponententransformation: ");
1500//reord->show();
1501//PrintLn();
1502  for (i=IDELEMS(e);i!=0;i--)
1503  {
1504    if (e->m[i-1]!=NULL)
1505    {
1506      p = e->m[i-1];
1507      while (p!=NULL)
1508      {
1509        j = pGetComp(p);
1510        pSetComp(p,(*reord)[j]);
1511        pIter(p);
1512      }
1513      e->m[i-1] = pOrdPolyMerge(e->m[i-1]);
1514    }
1515  }
1516  idSkipZeroes(e);
1517  delete reord;
1518  return e;
1519}
1520
1521/*
1522*computes a standard basis for h1 and stores the transformation matrix
1523* in ma
1524*/
1525ideal idLiftStd (ideal  h1,ideal  quot, matrix* ma, tHomog h)
1526{
1527  int   i, j, k=0, t, quotgen, inputIsIdeal=lengthFreeModule(h1);
1528  ideal e, h3;
1529  poly  p=NULL, q, qq;
1530  intvec *w=NULL;
1531
1532  idDelete((ideal*)ma);
1533  *ma=mpNew(1,0);
1534  if (idIs0(h1))
1535    return idInit(1,h1->rank);
1536  h3=idPrepare(h1,quot,h,&k,&quotgen,&i,&w);
1537  if (w!=NULL) delete w;
1538  i = 0;
1539  for (j=0;j<IDELEMS(h3);j++)
1540  {
1541    if ((h3->m[j] != NULL) && (pMinComp(h3->m[j]) <= k))
1542      i++;
1543  }
1544  j = IDELEMS(h1);
1545  idDelete((ideal*)ma);
1546  *ma = mpNew(j,i);
1547  i = -1;
1548  e=idInit(16,h1->rank);
1549  for (j=0; j<IDELEMS(h3); j++)
1550  {
1551    if ((h3->m[j] != NULL) && (pMinComp(h3->m[j]) <= k))
1552    {
1553      q = h3->m[j];
1554      qq=q;
1555      h3->m[j]=NULL;
1556      while (pNext(q) != NULL)
1557      {
1558        if (pGetComp(pNext(q)) > k)
1559        {
1560          p = pNext(q);
1561          pNext(q) = pNext(pNext(q));
1562          pNext(p) = NULL;
1563          t=pGetComp(p);
1564          pSetComp(p,0);
1565          MATELEM(*ma,t-k,i+2) = pAdd(MATELEM(*ma,t-k,i+2),p);
1566        }
1567        else
1568        {
1569          pIter(q);
1570        }
1571      }
1572      if (!inputIsIdeal) pShift(&qq,-1);
1573      //if (quotgen != 0)
1574      //{
1575      //  q = kNF(quot,qq);
1576      //  pDelete(&qq);
1577      //}
1578      //else
1579        q = qq;
1580      if (q !=NULL)
1581      {
1582        i++;
1583        if (i+1 >= IDELEMS(e))
1584        {
1585          pEnlargeSet(&(e->m),IDELEMS(e),16);
1586          IDELEMS(e) += 16;
1587        }
1588        e->m[i] = q;
1589      }
1590    }
1591  }
1592  idDelete(&h3);
1593  idSkipZeroes(e);
1594  return e;
1595}
1596
1597/*2
1598*computes a representation of the generators of submod with respect to those
1599* of mod
1600*/
1601ideal idLiftNonStB (ideal  mod, ideal submod,BOOLEAN goodShape)
1602{
1603  int   lsmod =idRankFreeModule(submod), i, j, k, quotgen;
1604  ideal result, h3, temp;
1605
1606  if (idIs0(mod))
1607    return idInit(1,mod->rank);
1608
1609  if  ((idRankFreeModule(mod)!=0) && (lsmod==0)) lsmod=1;
1610  k=lsmod;
1611  //idSkipZeroes(mod);
1612  h3=idPrepare(mod,currQuotient,(tHomog)FALSE,&k,&quotgen,&i,NULL);
1613  if (!goodShape)
1614  {
1615    for (j=0;j<IDELEMS(h3);j++)
1616    {
1617      if ((h3->m[j] != NULL) && (pMinComp(h3->m[j]) > k))
1618        pDelete(&(h3->m[j]));
1619    }
1620  }
1621  idSkipZeroes(h3);
1622  if (lsmod==0)
1623  {
1624    temp = idCopy(submod);
1625    for (j=IDELEMS(temp);j>0;j--)
1626    {
1627      if (temp->m[j-1]!=NULL)
1628        pShift(&(temp->m[j-1]),1);
1629    }
1630  }
1631  else
1632  {
1633    temp = submod;
1634  }
1635  pSetSyzComp(k);
1636  result = kNF(h3,currQuotient,temp,k);
1637  result->rank = h3->rank;
1638  idDelete(&h3);
1639  if (lsmod==0)
1640    idDelete(&temp);
1641  pSetSyzComp(0);
1642  for (j=0;j<IDELEMS(result);j++)
1643  {
1644    if (result->m[j]!=NULL)
1645    {
1646      if (pGetComp(result->m[j])<=k)
1647      {
1648        WerrorS("2nd module lies not in the first");
1649        idDelete(&result);
1650        return idInit(1,1);
1651      }
1652      else
1653      {
1654        pShift(&(result->m[j]),-k);
1655        pNeg(result->m[j]);
1656      }
1657    }
1658  }
1659  return result;
1660}
1661
1662/*2
1663*computes a representation of the generators of submod with respect to those
1664* of mod which is given as standardbasis,
1665* uses currQuotient as the quotient ideal (if not NULL)
1666*/
1667ideal  idLift (ideal  mod,ideal submod)
1668{
1669  ideal temp, result;
1670  int   j,k;
1671  poly  p,q;
1672  BOOLEAN reported=FALSE;
1673
1674  if (idIs0(mod)) return idInit(1,mod->rank);
1675  k = lengthFreeModule(mod);
1676  temp=idCopy(mod);
1677  if (k == 0)
1678  {
1679    for (j=0; j<IDELEMS(temp); j++)
1680    {
1681      if (temp->m[j]!=NULL) pSetCompP(temp->m[j],1);
1682    }
1683    k = 1;
1684  }
1685  for (j=0; j<IDELEMS(temp); j++)
1686  {
1687    if (temp->m[j]!=NULL)
1688    {
1689      p = temp->m[j];
1690      q = pOne();
1691      pGetCoeff(q)=nNeg(pGetCoeff(q));   //set q to -1
1692      pSetComp(q,k+1+j);
1693      while (pNext(p)) pIter(p);
1694      pNext(p) = q;
1695    }
1696  }
1697  result=idInit(IDELEMS(submod),submod->rank);
1698  pSetSyzComp(k);
1699  for (j=0; j<IDELEMS(submod); j++)
1700  {
1701    if (submod->m[j]!=NULL)
1702    {
1703      p = pCopy(submod->m[j]);
1704      if (pGetComp(p)==0) pSetCompP(p,1);
1705      q = kNF(temp,currQuotient,p);
1706      pDelete(&p);
1707      if (q!=NULL)
1708      {
1709        if (pMinComp(q)<=k)
1710        {
1711          if (!reported)
1712          {
1713            Warn("first module not a standardbasis");
1714            Warn("or second not a proper submodule");
1715            reported=TRUE;
1716          }
1717          pDelete(&q);
1718        }
1719        else
1720        {
1721          pShift(&q,-k);
1722          result->m[j] = q;
1723        }
1724      }
1725    }
1726  }
1727  pSetSyzComp(0);
1728  //idSkipZeroes(result);
1729  idDelete(&temp);
1730  return result;
1731}
1732
1733/*2
1734*computes the quotient of h1,h2
1735*/
1736#ifdef OLD_QUOT
1737ideal idQuot (ideal  h1, ideal h2, BOOLEAN h1IsSB, BOOLEAN resultIsIdeal)
1738{
1739  int i,j = 0,l,ll,k,kkk,k1,k2,kmax;
1740  ideal h3,h4;
1741  poly     p,q = NULL;
1742  BOOLEAN     b = FALSE;
1743
1744  k1 = lengthFreeModule(h1);
1745  k2 = lengthFreeModule(h2);
1746  k=max(k1,k2);
1747  if (k==0) { k = 1; b=TRUE; }
1748  h4 = idInit(1,1);
1749  for (i=0; i<IDELEMS(h2); i++)
1750  {
1751    if (h2->m[i] != NULL)
1752    {
1753      p = pCopy(h2->m[i]);
1754      if (k2 == 0)
1755        pShift(&p,j*k+1);
1756      else
1757        pShift(&p,j*k);
1758      q = pAdd(q,p);
1759      j++;
1760    }
1761  }
1762  kmax = j*k+1;
1763  p = pOne();
1764  pSetComp(p,kmax);
1765  pSetSyzComp(kmax-1);
1766  q = pAdd(q,p);
1767  h4->m[0] = q;
1768  if (k2 == 0)
1769  {
1770    if (k > IDELEMS(h4))
1771    {
1772      pEnlargeSet(&(h4->m),IDELEMS(h4),k-IDELEMS(h4));
1773      IDELEMS(h4) = k;
1774    }
1775    for (i=1; i<k; i++)
1776    {
1777      p = pCopy(h4->m[i-1]);
1778      pShift(&p,1);
1779      h4->m[i] = p;
1780    }
1781  }
1782  kkk = IDELEMS(h4);
1783  i = IDELEMS(h1);
1784  while (h1->m[i-1] == NULL) i--;
1785  for (l=0; l<i; l++)
1786  {
1787    if(h1->m[l]!=NULL)
1788    {
1789      for (ll=0; ll<j; ll++)
1790      {
1791        p = pCopy(h1->m[l]);
1792        if (k1 == 0)
1793          pShift(&p,ll*k+1);
1794        else
1795          pShift(&p,ll*k);
1796        if (kkk >= IDELEMS(h4))
1797        {
1798          pEnlargeSet(&(h4->m),IDELEMS(h4),16);
1799          IDELEMS(h4) += 16;
1800        }
1801        h4->m[kkk] = p;
1802        kkk++;
1803      }
1804    }
1805  }
1806  h3 = kStd(h4,currQuotient,(tHomog)FALSE,NULL,NULL,kmax-1);
1807  pSetSyzComp(0);
1808  idDelete(&h4);
1809  for (i=0;i<IDELEMS(h3);i++)
1810  {
1811    if ((h3->m[i]!=NULL) && (pGetComp(h3->m[i])>=kmax))
1812    {
1813      if (b)
1814        pShift(&h3->m[i],-kmax);
1815      else
1816        pShift(&h3->m[i],-kmax+1);
1817    }
1818    else
1819      pDelete(&h3->m[i]);
1820  }
1821  if (b)
1822    h3->rank = 1;
1823  else
1824    h3->rank = h1->rank;
1825  h4=idCompactify(h3);
1826  idDelete(&h3);
1827  return h4;
1828}
1829#else
1830ideal idQuot (ideal  h1, ideal h2, BOOLEAN h1IsStb, BOOLEAN resultIsIdeal)
1831{
1832  // first check for special case h1:(0)
1833  ideal h3;
1834  if (idIs0(h2))
1835  {
1836    if (resultIsIdeal)
1837    {
1838      h3 = idInit(1,1);
1839      h3->m[0] = pOne();
1840    }
1841    else
1842      h3 = idFreeModule(h1->rank);
1843    return h3;
1844  }
1845
1846  // the usual part:
1847  intvec * weights,* weights1;
1848  ideal h4,temph1;
1849  BITSET old_test=test;
1850  poly     p,q = NULL;
1851  int i,l,ll,k,kkk,kmax;
1852  int j = 0;
1853  int k1 = lengthFreeModule(h1);
1854  int k2 = lengthFreeModule(h2);
1855  BOOLEAN  addOnlyOne=TRUE;
1856  tHomog   hom=isNotHomog;
1857
1858  k=max(k1,k2);
1859  if (k==0)
1860  {
1861    k = 1;
1862    //resultIsIdeal=TRUE;
1863  }
1864  //else if ((k1>0)&&(k2>0))
1865  //{
1866  //  resultIsIdeal=TRUE;
1867  //}
1868  hom = (tHomog)idHomModule(h1,currQuotient,&weights) ;
1869  h4 = idInit(1,1);
1870  for (i=0; i<IDELEMS(h2); i++)
1871  {
1872    if (h2->m[i] != NULL)
1873    {
1874      p = pCopy(h2->m[i]);
1875      if (k2 == 0)
1876        pShift(&p,j*k+1);
1877      else
1878        pShift(&p,j*k);
1879      q = pAdd(q,p);
1880      j++;
1881    }
1882  }
1883  kmax = j*k+1;
1884  p = pOne();
1885  pSetComp(p,kmax);
1886  pSetSyzComp(kmax-1);
1887  q = pAdd(q,p);
1888  h4->m[0] = q;
1889  if (k2 == 0)
1890  {
1891    if (k > IDELEMS(h4))
1892    {
1893      pEnlargeSet(&(h4->m),IDELEMS(h4),k-IDELEMS(h4));
1894      IDELEMS(h4) = k;
1895    }
1896    if (k>1) addOnlyOne = FALSE;
1897    for (i=1; i<k; i++)
1898    {
1899      p = pCopy(h4->m[i-1]);
1900      pShift(&p,1);
1901      h4->m[i] = p;
1902    }
1903  }
1904  kkk = IDELEMS(h4);
1905  if (addOnlyOne && (!h1IsStb))
1906    temph1 = kStd(h1,currQuotient,hom,&weights,NULL);
1907  else
1908    temph1 = h1;
1909  idTest(temph1);
1910  i = IDELEMS(temph1);
1911  while ((i>0) && (temph1->m[i-1]==NULL)) i--;
1912  for (l=0; l<i; l++)
1913  {
1914    if(temph1->m[l]!=NULL)
1915    {
1916      for (ll=0; ll<j; ll++)
1917      {
1918        p = pCopy(temph1->m[l]);
1919        if (k1 == 0)
1920          pShift(&p,ll*k+1);
1921        else
1922          pShift(&p,ll*k);
1923        if (kkk >= IDELEMS(h4))
1924        {
1925          pEnlargeSet(&(h4->m),IDELEMS(h4),16);
1926          IDELEMS(h4) += 16;
1927        }
1928        h4->m[kkk] = p;
1929        kkk++;
1930      }
1931    }
1932  }
1933  idTest(h4);
1934  if (addOnlyOne)
1935  {
1936    p = h4->m[0];
1937    for (i=0;i<IDELEMS(h4)-1;i++)
1938    {
1939      h4->m[i] = h4->m[i+1];
1940    }
1941    h4->m[IDELEMS(h4)-1] = p;
1942    idSkipZeroes(h4);
1943    test |= Sy_bit(OPT_SB_1);
1944  }
1945  idTest(h4);
1946  hom = (tHomog)idHomModule(h4,currQuotient,&weights1);
1947  if (addOnlyOne)
1948  {
1949    h3 = kStd(h4,currQuotient,hom,&weights1,NULL,kmax-1,IDELEMS(h4)-1);
1950  }
1951  else
1952  {
1953    h3 = kStd(h4,currQuotient,hom,&weights1,NULL,kmax-1);
1954  }
1955  idTest(h3);
1956  idDelete(&h4);
1957  pSetSyzComp(0);
1958  for (i=0;i<IDELEMS(h3);i++)
1959  {
1960    if ((h3->m[i]!=NULL) && (pGetComp(h3->m[i])>=kmax))
1961    {
1962      if (resultIsIdeal)
1963        pShift(&h3->m[i],-kmax);
1964      else
1965        pShift(&h3->m[i],-kmax+1);
1966    }
1967    else
1968      pDelete(&h3->m[i]);
1969  }
1970  if (resultIsIdeal)
1971    h3->rank = 1;
1972  else
1973    h3->rank = h1->rank;
1974  idTest(h3);
1975  idSkipZeroes(h3);
1976  //h4=idCompactify(h3);
1977  //idDelete(&h3);
1978  if ((addOnlyOne) && (!h1IsStb))
1979    idDelete(&temph1);
1980  if (weights!=NULL) delete weights;
1981  if (weights1!=NULL) delete weights1;
1982  test = old_test;
1983  return h3;
1984}
1985#endif
1986
1987/*2
1988*computes recursively all monomials of a certain degree
1989*in every step the actvar-th entry in the exponential
1990*vector is incremented and the other variables are
1991*computed by recursive calls of makemonoms
1992*if the last variable is reached, the difference to the
1993*degree is computed directly
1994*vars is the number variables
1995*actvar is the actual variable to handle
1996*deg is the degree of the monomials to compute
1997*monomdeg is the actual degree of the monomial in consideration
1998*/
1999static void makemonoms(int vars,int actvar,int deg,int monomdeg)
2000{
2001  poly p;
2002  int i=0;
2003
2004  if ((idpowerpoint == 0) && (actvar ==1))
2005  {
2006    idpower[idpowerpoint] = pOne();
2007    monomdeg = 0;
2008  }
2009  while (i<=deg)
2010  {
2011    if (deg == monomdeg)
2012    {
2013      pSetm(idpower[idpowerpoint]);
2014      idpowerpoint++;
2015      return;
2016    }
2017    if (actvar == vars)
2018    {
2019      pSetExp(idpower[idpowerpoint],actvar,deg-monomdeg);
2020      pSetm(idpower[idpowerpoint]);
2021      idpowerpoint++;
2022      return;
2023    }
2024    else
2025    {
2026      p = pCopy(idpower[idpowerpoint]);
2027      makemonoms(vars,actvar+1,deg,monomdeg);
2028      idpower[idpowerpoint] = p;
2029    }
2030    monomdeg++;
2031    pSetExp(idpower[idpowerpoint],actvar,pGetExp(idpower[idpowerpoint],actvar)+1);
2032    pSetm(idpower[idpowerpoint]);
2033    i++;
2034  }
2035}
2036
2037/*2
2038*returns the deg-th power of the maximal ideal of 0
2039*/
2040ideal idMaxIdeal(int deg)
2041{
2042  if (deg < 0)
2043  {
2044    WarnS("maxideal: power must be non-negative");
2045  }
2046  if (deg < 1)
2047  {
2048    ideal I=idInit(1,1);
2049    I->m[0]=pOne();
2050    return I;
2051  }
2052  if (deg == 1)
2053  {
2054    return idMaxIdeal();
2055  }
2056
2057  int vars = currRing->N;
2058  int i = binom(vars+deg-1,deg);
2059  ideal id=idInit(i,1);
2060  idpower = id->m;
2061  idpowerpoint = 0;
2062  makemonoms(vars,1,deg,0);
2063  idpower = NULL;
2064  idpowerpoint = 0;
2065  return id;
2066}
2067
2068/*2
2069*computes recursively all generators of a certain degree
2070*of the ideal "givenideal"
2071*elms is the number elements in the given ideal
2072*actelm is the actual element to handle
2073*deg is the degree of the power to compute
2074*gendeg is the actual degree of the generator in consideration
2075*/
2076static void makepotence(int elms,int actelm,int deg,int gendeg)
2077{
2078  poly p;
2079  int i=0;
2080
2081  if ((idpowerpoint == 0) && (actelm ==1))
2082  {
2083    idpower[idpowerpoint] = pOne();
2084    gendeg = 0;
2085  }
2086  while (i<=deg)
2087  {
2088    if (deg == gendeg)
2089    {
2090      idpowerpoint++;
2091      return;
2092    }
2093    if (actelm == elms)
2094    {
2095      p=pPower(pCopy(givenideal[actelm-1]),deg-gendeg);
2096      idpower[idpowerpoint]=pMult(idpower[idpowerpoint],p);
2097      idpowerpoint++;
2098      return;
2099    }
2100    else
2101    {
2102      p = pCopy(idpower[idpowerpoint]);
2103      makepotence(elms,actelm+1,deg,gendeg);
2104      idpower[idpowerpoint] = p;
2105    }
2106    gendeg++;
2107    idpower[idpowerpoint]=pMult(idpower[idpowerpoint],pCopy(givenideal[actelm-1]));
2108    i++;
2109  }
2110}
2111
2112/*2
2113*returns the deg-th power of the ideal gid
2114*/
2115//ideal idPower(ideal gid,int deg)
2116//{
2117//  int i;
2118//  ideal id;
2119//
2120//  if (deg < 1) deg = 1;
2121//  i = binom(IDELEMS(gid)+deg-1,deg);
2122//  id=idInit(i,1);
2123//  idpower = id->m;
2124//  givenideal = gid->m;
2125//  idpowerpoint = 0;
2126//  makepotence(IDELEMS(gid),1,deg,0);
2127//  idpower = NULL;
2128//  givenideal = NULL;
2129//  idpowerpoint = 0;
2130//  return id;
2131//}
2132static void idNextPotence(ideal given, ideal result,
2133  int begin, int end, int deg, int restdeg, poly ap)
2134{
2135  poly p;
2136  int i;
2137
2138  p = pPower(pCopy(given->m[begin]),restdeg);
2139  i = result->nrows;
2140  result->m[i] = pMult(pCopy(ap),p);
2141//PrintS(".");
2142  (result->nrows)++;
2143  if (result->nrows >= IDELEMS(result))
2144  {
2145    pEnlargeSet(&(result->m),IDELEMS(result),16);
2146    IDELEMS(result) += 16;
2147  }
2148  if (begin == end) return;
2149  for (i=restdeg-1;i>=0;i--)
2150  {
2151    p = pPower(pCopy(given->m[begin]),i);
2152    p = pMult(pCopy(ap),p);
2153    idNextPotence(given, result, begin+1, end, deg, restdeg-i, p);
2154    pDelete(&p);
2155  }
2156}
2157
2158ideal idPower(ideal given,int exp)
2159{
2160  ideal result,temp;
2161  poly p1;
2162  int i;
2163
2164  if (idIs0(given)) return idInit(1,1);
2165  temp = idCopy(given);
2166  idSkipZeroes(temp);
2167  i = binom(IDELEMS(temp)+exp-1,exp);
2168  result = idInit(i,1);
2169  result->nrows = 0;
2170//Print("ideal contains %d elements\n",i);
2171  p1=pOne();
2172  idNextPotence(temp,result,0,IDELEMS(temp)-1,exp,exp,p1);
2173  pDelete(&p1);
2174  idDelete(&temp);
2175  result->nrows = 1;
2176  idSkipZeroes(result);
2177  idDelEquals(result);
2178  return result;
2179}
2180
2181/*2
2182* eliminate delVar (product of vars) in h1
2183*/
2184ideal idElimination (ideal h1,poly delVar,intvec *hilb)
2185{
2186  int    i,j=0,k,l;
2187  ideal  h,hh, h3;
2188  int    *ord,*block0,*block1;
2189  int    ordersize=2;
2190  short  **wv;
2191  tHomog hom;
2192  intvec * w;
2193  sip_sring tmpR;
2194  ring origR = currRing;
2195
2196  if (delVar==NULL)
2197  {
2198    return idCopy(h1);
2199  }
2200  if (currQuotient!=NULL)
2201  {
2202    WerrorS("cannot eliminate in a qring");
2203    return idCopy(h1);
2204  }
2205  if (idIs0(h1)) return idInit(1,h1->rank);
2206  hom=(tHomog)idHomModule(h1,NULL,&w); //sets w to weight vector or NULL
2207  h3=idInit(16,h1->rank);
2208  for (k=0;; k++)
2209  {
2210    if (currRing->order[k]!=0) ordersize++;
2211    else break;
2212  }
2213  ord=(int*)Alloc0(ordersize*sizeof(int));
2214  block0=(int*)Alloc(ordersize*sizeof(int));
2215  block1=(int*)Alloc(ordersize*sizeof(int));
2216  for (k=0;; k++)
2217  {
2218    if (currRing->order[k]!=0)
2219    {
2220      block0[k+1] = currRing->block0[k];
2221      block1[k+1] = currRing->block1[k];
2222      ord[k+1] = currRing->order[k];
2223    }
2224    else
2225      break;
2226  }
2227  block0[0] = 1;
2228  block1[0] = pVariables;
2229  wv=(short**) Alloc0(ordersize*sizeof(short**));
2230  memcpy4(wv+1,currRing->wvhdl,(ordersize-1)*sizeof(short**));
2231  wv[0]=(short*)Alloc0((pVariables+1)*sizeof(short));
2232  for (j=0;j<pVariables;j++)
2233    if (pGetExp(delVar,j+1)!=0) wv[0][j]=1;
2234  ord[0] = ringorder_a;
2235
2236  // fill in tmp ring to get back the data later on
2237  tmpR  = *origR;
2238  tmpR.order = ord;
2239  tmpR.block0 = block0;
2240  tmpR.block1 = block1;
2241  tmpR.wvhdl = wv;
2242  rComplete(&tmpR);
2243
2244  // change into the new ring
2245  //pChangeRing(pVariables,currRing->OrdSgn,ord,block0,block1,wv);
2246  rChangeCurrRing(&tmpR, TRUE);
2247  currRing = &tmpR;
2248  h = idInit(IDELEMS(h1),1);
2249  // fetch data from the old ring
2250  for (k=0;k<IDELEMS(h1);k++) h->m[k] = pFetchCopy(origR, h1->m[k]);
2251  // compute kStd
2252  hh = kStd(h,NULL,hom,&w,hilb);
2253  idDelete(&h);
2254
2255  // go back to the original ring
2256  rChangeCurrRing(origR,TRUE);
2257  i = IDELEMS(hh)-1;
2258  while ((i >= 0) && (hh->m[i] == NULL)) i--;
2259  j = -1;
2260  // fetch data from temp ring
2261  for (k=0; k<=i; k++)
2262  {
2263    l=pVariables;
2264    while ((l>0) && (pRingGetExp(&tmpR, hh->m[k],l)*pGetExp(delVar,l)==0)) l--;
2265    if (l==0)
2266    {
2267      j++;
2268      if (j >= IDELEMS(h3))
2269      {
2270        pEnlargeSet(&(h3->m),IDELEMS(h3),16);
2271        IDELEMS(h3) += 16;
2272      }
2273      h3->m[j] = pFetchCopy(&tmpR, hh->m[k]);
2274    }
2275  }
2276  idDelete(&hh);
2277  idSkipZeroes(h3);
2278  Free((ADDRESS)wv[0],(pVariables+1)*sizeof(short));
2279  Free((ADDRESS)wv,ordersize*sizeof(short**));
2280  Free((ADDRESS)ord,ordersize*sizeof(int));
2281  Free((ADDRESS)block0,ordersize*sizeof(int));
2282  Free((ADDRESS)block1,ordersize*sizeof(int));
2283  if (w!=NULL)
2284    delete w;
2285  return h3;
2286}
2287
2288//void idEnterSet (poly p,ideal r, int * next)
2289//{
2290//
2291//  if ((*next) == IDELEMS(r)-1)
2292//  {
2293//    pEnlargeSet(&(r->m),IDELEMS(r),16);
2294//    IDELEMS(r)+=16;
2295//  }
2296//  int at;
2297//  int i;
2298//  if (*next==0) at=0;
2299//  else
2300//  {
2301//    int an = 0;
2302//    int en= *next-1;
2303//    int c;
2304//    if (pComp0(r->m[(*next)-1],p)!= 1)
2305//      at=*next;
2306//    else
2307//    {
2308//      loop
2309//      {
2310//        if (an >= en-1)
2311//        {
2312//          if (pComp0(r->m[an],p) == 1)
2313//          {
2314//            at=an; break;
2315//          }
2316//          else
2317//          {
2318//            at=en; break;
2319//          }
2320//        }
2321//        i=(an+en) / 2;
2322//        if (pComp0(r->m[i],p) == 1) en=i;
2323//        else                       an=i;
2324//      }
2325//    }
2326//  }
2327//  if (pComp(r->m[at],p)==0)
2328//  {
2329//    pDelete(&p);
2330//  }
2331//  else
2332//  {
2333//    (*next)++;
2334//    for (i=(*next); i>=at+1; i--)
2335//    {
2336//      r->m[i] = r->m[i-1];
2337//    }
2338//    /*- save result -*/
2339//    r->m[at] = p;
2340//  }
2341//}
2342/*3
2343* produces recursively the ideal of all arxar-minors of a
2344*/
2345static void idRecMin(matrix a,int ar,poly *barDiv,ideal result,
2346              int * nextPlace, int rowToChose=0)
2347{
2348//Print("Level: %d\n",ar);
2349/*--- there is no non-zero minor coming from a------------*/
2350  if((ar<0) || (ar>min(a->ncols,a->nrows)-1))
2351  {
2352    idDelete((ideal *)&a);
2353    pDelete(barDiv);
2354    return;
2355  }
2356
2357/*--- initializing temporary structures-------------------*/
2358  int i,j,r=rowToChose,c,newi,newp,k;
2359  poly p=NULL;
2360
2361  if (ar==0)
2362  {
2363/*--- ar is 0, the matrix-entres are minors---------------*/
2364    for (i=a->nrows;i>0;i--)
2365    {
2366      for (j=a->ncols;j>0;j--)
2367      {
2368        p = MATELEM(a,i,j);
2369        if (p!=NULL)
2370        {
2371          //idEnterSet(p,result,nextPlace);
2372          if (*nextPlace>=IDELEMS(result))
2373          {
2374            pEnlargeSet(&(result->m),IDELEMS(result),IDELEMS(result));
2375            IDELEMS(result) *=2;
2376          }
2377          result->m[*nextPlace] = p;
2378          (*nextPlace)++;
2379          MATELEM(a,i,j) = NULL;
2380        }
2381      }
2382    }
2383    idTest(result);
2384    idDelete((ideal*)&a);
2385    pDelete(barDiv);
2386    return;
2387  }
2388/*--- ar>0, we perform one step of the Bareiss algorithm--*/
2389  p = pCopy(*barDiv);   //we had to store barDiv for the remaining loops
2390  matrix nextStep = mpOneStepBareiss(a,barDiv,&r,&c);
2391//Print("next row is: %d, next col: %d\n",r,c);
2392/*--- there is no pivot - the det of matrix is zero -------------*/
2393  if ((r*c==0) || (MATELEM(nextStep,nextStep->nrows,nextStep->ncols)==NULL))
2394  {
2395    idDelete((ideal*)&nextStep);
2396    idDelete((ideal*)&a);
2397    pDelete(&p);
2398    // pDelete(barDiv); barDiv==NULL in this case
2399    return;
2400  }
2401/*--- we read out the r-1 x c-1 matrix for the next step--*/
2402  if ((a->nrows-1)*(a->ncols-1)>0)
2403  {
2404    matrix next = mpNew(a->nrows-1,a->ncols-1);
2405    for (i=a->nrows-1;i>0;i--)
2406    {
2407      for (j=a->ncols-1;j>0;j--)
2408      {
2409        MATELEM(next,i,j) = MATELEM(nextStep,i,j);
2410        MATELEM(nextStep,i,j) =NULL;
2411      }
2412    }
2413    idDelete((ideal*)&nextStep);
2414/*--- we call the next Step------------------------------*/
2415    idRecMin(next,ar-1,barDiv,result,nextPlace);
2416    next = NULL;
2417  }
2418  if ((*barDiv)!=NULL) pDelete(barDiv);
2419/*--- now we have to take out the r-th row...------------*/
2420  if (((a->nrows)>1) && (rowToChose==0))
2421  {
2422    if (nextStep!=NULL) idDelete((ideal*)&nextStep);
2423    nextStep = mpNew(a->nrows-1,a->ncols);
2424    for (i=r-1;i>0;i--)
2425    {
2426      for (j=a->ncols;j>0;j--)
2427      {
2428        MATELEM(nextStep,i,j) = pCopy(MATELEM(a,i,j));
2429      }
2430    }
2431    for (i=a->nrows;i>r;i--)
2432    {
2433      for (j=a->ncols;j>0;j--)
2434      {
2435        MATELEM(nextStep,i-1,j) = pCopy(MATELEM(a,i,j));
2436      }
2437    }
2438/*--- and to perform the algorithm with the rest---------*/
2439    poly q=pCopy(p);
2440    idRecMin(nextStep,ar,&q,result,nextPlace);
2441    assume(q==NULL);
2442    nextStep = NULL;
2443  }
2444/*--- now we have to take out the c-th col...------------*/
2445  if ((a->nrows)>1)
2446  {
2447    if (nextStep!=NULL) idDelete((ideal*)&nextStep);
2448    nextStep = mpNew(a->nrows,a->ncols-1);
2449    for (i=a->nrows;i>0;i--)
2450    {
2451      for (j=c-1;j>0;j--)
2452      {
2453        MATELEM(nextStep,i,j) = MATELEM(a,i,j);
2454        MATELEM(a,i,j) = NULL;
2455      }
2456    }
2457    for (i=a->nrows;i>0;i--)
2458    {
2459      for (j=a->ncols;j>c;j--)
2460      {
2461        MATELEM(nextStep,i,j-1) = MATELEM(a,i,j);
2462        MATELEM(a,i,j) = NULL;
2463      }
2464    }
2465/*--- and to perform the algorithm with the rest---------*/
2466    idDelete((ideal*)&a);
2467    idRecMin(nextStep,ar,&p,result,nextPlace,r);
2468    //assume(p==NULL);
2469    nextStep = NULL;
2470  }
2471/*--- deleting temporary structures and returns----------*/
2472  pDelete(&p);
2473  return;
2474}
2475
2476#ifdef WITH_OLD_MINOR
2477/*2
2478* compute all ar-minors of the matrix a
2479*/
2480ideal idMinors(matrix a, int ar)
2481{
2482  int     i,j,k,size;
2483  int *rowchoise,*colchoise;
2484  BOOLEAN rowch,colch;
2485  ideal result;
2486  matrix tmp;
2487  poly p;
2488
2489  i = binom(a->rows(),ar);
2490  j = binom(a->cols(),ar);
2491
2492  rowchoise=(int *)Alloc(ar*sizeof(int));
2493  colchoise=(int *)Alloc(ar*sizeof(int));
2494  if ((i>512) || (j>512) || (i*j >512)) size=512;
2495  else size=i*j;
2496  result=idInit(size,1);
2497  tmp=mpNew(ar,ar);
2498  k = 0; /* the index in result*/
2499  idInitChoise(ar,1,a->rows(),&rowch,rowchoise);
2500  while (!rowch)
2501  {
2502    idInitChoise(ar,1,a->cols(),&colch,colchoise);
2503    while (!colch)
2504    {
2505      for (i=1; i<=ar; i++)
2506      {
2507        for (j=1; j<=ar; j++)
2508        {
2509          MATELEM(tmp,i,j) = MATELEM(a,rowchoise[i-1],colchoise[j-1]);
2510        }
2511      }
2512      p = mpDetBareiss(tmp);
2513      if (p!=NULL)
2514      {
2515        if (k>=size)
2516        {
2517          pEnlargeSet(&result->m,size,32);
2518          size += 32;
2519        }
2520        result->m[k] = p;
2521        k++;
2522      }
2523      idGetNextChoise(ar,a->cols(),&colch,colchoise);
2524    }
2525    idGetNextChoise(ar,a->rows(),&rowch,rowchoise);
2526  }
2527  /*delete the matrix tmp*/
2528  for (i=1; i<=ar; i++)
2529  {
2530    for (j=1; j<=ar; j++) MATELEM(tmp,i,j) = NULL;
2531  }
2532  idDelete((ideal*)&tmp);
2533  if (k==0)
2534  {
2535    k=1;
2536    result->m[0]=NULL;
2537  }
2538  Free((ADDRESS)rowchoise,ar*sizeof(int));
2539  Free((ADDRESS)colchoise,ar*sizeof(int));
2540  pEnlargeSet(&result->m,size,k-size);
2541  IDELEMS(result) = k;
2542  return (result);
2543}
2544#else
2545/*2
2546* compute all ar-minors of the matrix a
2547* the caller of idRecMin
2548*/
2549ideal idMinors(matrix a, int ar)
2550{
2551  if((ar<=0) || (ar>min(a->ncols,a->nrows)))
2552  {
2553    Werror("%d-th minor, matrix is %dx%d",ar,a->ncols,a->nrows);
2554    return NULL;
2555  }
2556  int i=0;
2557  poly barDiv=NULL;
2558  ideal result=idInit(16,1);
2559  if (a->ncols>=a->nrows)
2560  {
2561    idRecMin(mpCopy(a),ar-1,&barDiv,result,&i);
2562  }
2563  else
2564  {
2565    idRecMin(mpTransp(a),ar-1,&barDiv,result,&i);
2566  }
2567  idSkipZeroes(result);
2568  return result;
2569}
2570#endif
2571
2572
2573/*2
2574*returns TRUE if p is a unit element in the current ring
2575*/
2576BOOLEAN pIsUnit(poly p)
2577{
2578  int i;
2579
2580  if (p == NULL) return FALSE;
2581  i = 1;
2582  while (i<=pVariables && pGetExp(p,i) == 0) i++;
2583  if (i > pVariables && (pGetComp(p) == 0))
2584  {
2585    if (currRing->OrdSgn == 1 && pNext(p) !=NULL) return FALSE;
2586    return TRUE;
2587  }
2588  return FALSE;
2589}
2590
2591/*2
2592*skips all zeroes and double elements, searches also for units
2593*/
2594ideal idCompactify(ideal id)
2595{
2596  int i,j;
2597  BOOLEAN b=FALSE;
2598
2599  i = IDELEMS(id)-1;
2600  while ((! b) && (i>=0))
2601  {
2602    b=pIsUnit(id->m[i]);
2603    i--;
2604  }
2605  if (b)
2606  {
2607    ideal result=idInit(1,id->rank);
2608    result->m[0]=pOne();
2609    return result;
2610  }
2611  else
2612  {
2613    ideal result=idCopy(id);
2614    for (i=1;i<IDELEMS(result);i++)
2615    {
2616      if (result->m[i]!=NULL)
2617      {
2618        for (j=0;j<i;j++)
2619        {
2620          if ((result->m[j]!=NULL)
2621          && (pComparePolys(result->m[i],result->m[j])))
2622          {
2623            pDelete(&(result->m[j]));
2624          }
2625        }
2626      }
2627    }
2628    idSkipZeroes(result);
2629    return result;
2630  }
2631}
2632
2633/*2
2634*returns TRUE if id1 is a submodule of id2
2635*/
2636BOOLEAN idIsSubModule(ideal id1,ideal id2)
2637{
2638  int i;
2639  poly p;
2640
2641  if (idIs0(id1)) return TRUE;
2642  for (i=0;i<IDELEMS(id1);i++)
2643  {
2644    if (id1->m[i] != NULL)
2645    {
2646      p = kNF(id2,currQuotient,id1->m[i]);
2647      if (p != NULL)
2648      {
2649        pDelete(&p);
2650        return FALSE;
2651      }
2652    }
2653  }
2654  return TRUE;
2655}
2656
2657/*2
2658* returns the ideals of initial terms
2659*/
2660ideal idHead(ideal h)
2661{
2662  ideal m = idInit(IDELEMS(h),h->rank);
2663  int i;
2664
2665  for (i=IDELEMS(h)-1;i>=0; i--)
2666  {
2667    if (h->m[i]!=NULL) m->m[i]=pHead(h->m[i]);
2668  }
2669  return m;
2670}
2671
2672ideal idHomogen(ideal h, int varnum)
2673{
2674  ideal m = idInit(IDELEMS(h),h->rank);
2675  int i;
2676
2677  for (i=IDELEMS(h)-1;i>=0; i--)
2678  {
2679    m->m[i]=pHomogen(h->m[i],varnum);
2680  }
2681  return m;
2682}
2683
2684/*------------------type conversions----------------*/
2685ideal idVec2Ideal(poly vec)
2686{
2687   ideal result=idInit(1,1);
2688   Free((ADDRESS)result->m,sizeof(poly));
2689   result->m=NULL; // remove later
2690   pVec2Polys(vec, &(result->m), &(IDELEMS(result)));
2691   return result;
2692}
2693
2694ideal idMatrix2Module(matrix mat)
2695{
2696  ideal result = idInit(MATCOLS(mat),MATROWS(mat));
2697  int i,j;
2698  poly h;
2699#ifdef DRING
2700  poly p;
2701#endif
2702
2703  for(j=0;j<MATCOLS(mat);j++) /* j is also index in result->m */
2704  {
2705    for (i=1;i<=MATROWS(mat);i++)
2706    {
2707      h = MATELEM(mat,i,j+1);
2708      if (h!=NULL)
2709      {
2710        MATELEM(mat,i,j+1)=NULL;
2711        pSetCompP(h,i);
2712#ifdef DRING
2713        pdSetDFlagP(h,0);
2714#endif
2715        result->m[j] = pAdd(result->m[j],h);
2716      }
2717    }
2718  }
2719  return result;
2720}
2721
2722/*2
2723* converts a module into a matrix, destroyes the input
2724*/
2725matrix idModule2Matrix(ideal mod)
2726{
2727  matrix result = mpNew(mod->rank,IDELEMS(mod));
2728  int i,cp;
2729  poly p,h;
2730
2731  for(i=0;i<IDELEMS(mod);i++)
2732  {
2733    p=mod->m[i];
2734    mod->m[i]=NULL;
2735    while (p!=NULL)
2736    {
2737      h=p;
2738      pIter(p);
2739      pNext(h)=NULL;
2740//      cp = max(1,pGetComp(h));     // if used for ideals too
2741      cp = pGetComp(h);
2742      pSetComp(h,0);
2743#ifdef TEST
2744      if (cp>mod->rank)
2745      {
2746        Print("## inv. rank %d -> %d\n",mod->rank,cp);
2747        int k,l,o=mod->rank;
2748        mod->rank=cp;
2749        matrix d=mpNew(mod->rank,IDELEMS(mod));
2750        for (l=1; l<=o; l++)
2751        {
2752          for (k=1; k<=IDELEMS(mod); k++)
2753          {
2754            MATELEM(d,l,k)=MATELEM(result,l,k);
2755            MATELEM(result,l,k)=NULL;
2756          }
2757        }
2758        idDelete((ideal *)&result);
2759        result=d;
2760      }
2761#endif
2762      MATELEM(result,cp,i+1) = pAdd(MATELEM(result,cp,i+1),h);
2763    }
2764  }
2765  return result;
2766}
2767
2768matrix idModule2formatedMatrix(ideal mod,int rows, int cols)
2769{
2770  matrix result = mpNew(rows,cols);
2771  int i,cp,r=idRankFreeModule(mod),c=IDELEMS(mod);
2772  poly p,h;
2773
2774  if (r>rows) r = rows;
2775  if (c>cols) c = cols;
2776  for(i=0;i<c;i++)
2777  {
2778    p=mod->m[i];
2779    mod->m[i]=NULL;
2780    while (p!=NULL)
2781    {
2782      h=p;
2783      pIter(p);
2784      pNext(h)=NULL;
2785      cp = pGetComp(h);
2786      if (cp<=r)
2787      {
2788        pSetComp(h,0);
2789        MATELEM(result,cp,i+1) = pAdd(MATELEM(result,cp,i+1),h);
2790      }
2791      else
2792        pDelete(&h);
2793    }
2794  }
2795  idDelete(&mod);
2796  return result;
2797}
2798
2799/*2
2800* substitute the n-th variable by the monomial e in id
2801* destroy id
2802*/
2803ideal  idSubst(ideal id, int n, poly e)
2804{
2805  int k=MATROWS((matrix)id)*MATCOLS((matrix)id);
2806  ideal res=(ideal)mpNew(MATROWS((matrix)id),MATCOLS((matrix)id));
2807
2808  res->rank = id->rank;
2809  for(k--;k>=0;k--)
2810  {
2811    res->m[k]=pSubst(id->m[k],n,e);
2812    id->m[k]=NULL;
2813  }
2814  idDelete(&id);
2815  return res;
2816}
2817
2818BOOLEAN idHomModule(ideal m, ideal Q, intvec **w)
2819{
2820  if (w!=NULL) *w=NULL;
2821  if ((Q!=NULL) && (!idHomIdeal(Q,NULL))) return FALSE;
2822  if (idIs0(m)) return TRUE;
2823
2824  int i,j,cmax=2,order=0,ord,* diff,* iscom,diffmin=32000;
2825  poly p=NULL;
2826  int length=IDELEMS(m);
2827  polyset P=m->m;
2828  polyset F=(polyset)Alloc(length*sizeof(poly));
2829  for (i=length-1;i>=0;i--)
2830  {
2831    p=F[i]=P[i];
2832    cmax=max(cmax,pMaxComp(p)+1);
2833  }
2834  diff = (int *)Alloc0(cmax*sizeof(int));
2835  if (w!=NULL) *w=new intvec(cmax-1);
2836  iscom = (int *)Alloc0(cmax*sizeof(int));
2837  i=0;
2838  while (i<=length)
2839  {
2840    if (i<length)
2841    {
2842      p=F[i];
2843      while ((p!=NULL) && (!iscom[pGetComp(p)])) pIter(p);
2844    }
2845    if ((p==NULL) && (i<length))
2846    {
2847      i++;
2848    }
2849    else
2850    {
2851      if (p==NULL)
2852      {
2853        i=0;
2854        while ((i<length) && (F[i]==NULL)) i++;
2855        if (i>=length) break;
2856        p = F[i];
2857      }
2858      if (pLexOrder)
2859        order=pTotaldegree(p);
2860      else
2861      //  order = p->order;
2862        order = pFDeg(p);
2863      order += diff[pGetComp(p)];
2864      p = F[i];
2865//Print("Actual p=F[%d]: ",i);pWrite(p);
2866      F[i] = NULL;
2867      i=0;
2868    }
2869    while (p!=NULL)
2870    {
2871      //if (pLexOrder)
2872      //  ord=pTotaldegree(p);
2873      //else
2874      //  ord = p->order;
2875      ord = pFDeg(p);
2876      if (!iscom[pGetComp(p)])
2877      {
2878        diff[pGetComp(p)] = order-ord;
2879        iscom[pGetComp(p)] = 1;
2880/*
2881*PrintS("new diff: ");
2882*for (j=0;j<cmax;j++) Print("%d ",diff[j]);
2883*PrintLn();
2884*PrintS("new iscom: ");
2885*for (j=0;j<cmax;j++) Print("%d ",iscom[j]);
2886*PrintLn();
2887*Print("new set %d, order %d, ord %d, diff %d\n",pGetComp(p),order,ord,diff[pGetComp(p)]);
2888*/
2889      }
2890      else
2891      {
2892/*
2893*PrintS("new diff: ");
2894*for (j=0;j<cmax;j++) Print("%d ",diff[j]);
2895*PrintLn();
2896*Print("order %d, ord %d, diff %d\n",order,ord,diff[pGetComp(p)]);
2897*/
2898        if (order != ord+diff[pGetComp(p)])
2899        {
2900          Free((ADDRESS) iscom,cmax*sizeof(int));
2901          Free((ADDRESS) diff,cmax*sizeof(int));
2902          Free((ADDRESS) F,length*sizeof(poly));
2903          delete *w;*w=NULL;
2904          return FALSE;
2905        }
2906      }
2907      pIter(p);
2908    }
2909  }
2910  Free((ADDRESS) iscom,cmax*sizeof(int));
2911  Free((ADDRESS) F,length*sizeof(poly));
2912  for (i=1;i<cmax;i++) (**w)[i-1]=diff[i];
2913  for (i=1;i<cmax;i++)
2914  {
2915    if (diff[i]<diffmin) diffmin=diff[i];
2916  }
2917  for (i=1;i<cmax;i++)
2918  {
2919    (**w)[i-1]=diff[i]-diffmin;
2920  }
2921  Free((ADDRESS) diff,cmax*sizeof(int));
2922  return TRUE;
2923}
2924
2925ideal idJet(ideal i,int d)
2926{
2927  ideal r=idInit(IDELEMS(i),i->rank);
2928  int k;
2929  for(k=0; k<IDELEMS(i); k++)
2930  {
2931    r->m[k]=pJet(i->m[k],d);
2932  }
2933  return r;
2934}
2935
2936ideal idJetW(ideal i,int d, intvec * iv)
2937{
2938  ideal r=idInit(IDELEMS(i),i->rank);
2939  if (ecartWeights!=NULL)
2940  {
2941    WerrorS("cannot compute weighted jets now");
2942  }
2943  else
2944  {
2945    short *w=iv2array(iv);
2946    int k;
2947    for(k=0; k<IDELEMS(i); k++)
2948    {
2949      r->m[k]=pJetW(i->m[k],d,w);
2950    }
2951    Free((ADDRESS)w,(pVariables+1)*sizeof(short));
2952  }
2953  return r;
2954}
2955
2956matrix idDiff(matrix i, int k)
2957{
2958  int e=MATCOLS(i)*MATROWS(i);
2959  matrix r=mpNew(MATROWS(i),MATCOLS(i));
2960  int j;
2961  for(j=0; j<e; j++)
2962  {
2963    r->m[j]=pDiff(i->m[j],k);
2964  }
2965  return r;
2966}
2967
2968matrix idDiffOp(ideal I, ideal J,BOOLEAN multiply)
2969{
2970  matrix r=mpNew(IDELEMS(I),IDELEMS(J));
2971  int i,j;
2972  for(i=0; i<IDELEMS(I); i++)
2973  {
2974    for(j=0; j<IDELEMS(J); j++)
2975    {
2976      MATELEM(r,i+1,j+1)=pDiffOp(I->m[i],J->m[j],multiply);
2977    }
2978  }
2979  return r;
2980}
2981
2982/*2
2983* represents (h1+h2)/h2=h1/(h1 intersect h2)
2984*/
2985ideal idModulo (ideal h2,ideal h1)
2986{
2987  ideal temp,temp1;
2988  int i,j,k,rk,flength=0,slength,length;
2989  intvec * w;
2990  poly p,q;
2991
2992  if (idIs0(h2))
2993    return idFreeModule(max(1,h2->ncols));
2994  if (!idIs0(h1))
2995    flength = idRankFreeModule(h1);
2996  slength = idRankFreeModule(h2);
2997  length  = max(flength,slength);
2998  if (length==0)
2999  {
3000    length = 1;
3001  }
3002  temp = idInit(IDELEMS(h2),1);
3003  for (i=0;i<IDELEMS(h2);i++)
3004  {
3005    temp->m[i] = pCopy(h2->m[i]);
3006    q = pOne();
3007    pSetComp(q,i+1+length);
3008    if(temp->m[i]!=NULL)
3009    {
3010      if (slength==0) pShift(&(temp->m[i]),1);
3011      p = temp->m[i];
3012      while (pNext(p)!=NULL) pIter(p);
3013      pNext(p) = q;
3014    }
3015    else
3016      temp->m[i]=q;
3017  }
3018  rk = k = IDELEMS(h2);
3019  if (!idIs0(h1))
3020  {
3021    pEnlargeSet(&(temp->m),IDELEMS(temp),IDELEMS(h1));
3022    IDELEMS(temp) += IDELEMS(h1);
3023    for (i=0;i<IDELEMS(h1);i++)
3024    {
3025      if (h1->m[i]!=NULL)
3026      {
3027        temp->m[k] = pCopy(h1->m[i]);
3028        if (flength==0) pShift(&(temp->m[k]),1);
3029        k++;
3030      }
3031    }
3032  }
3033  pSetSyzComp(length);
3034  temp1 = kStd(temp,currQuotient,testHomog,&w,NULL,length);
3035  pSetSyzComp(0);
3036  idDelete(&temp);
3037  if (w!=NULL) delete w;
3038  for (i=0;i<IDELEMS(temp1);i++)
3039  {
3040    if ((temp1->m[i]!=NULL)
3041    && (pGetComp(temp1->m[i])<=length))
3042    {
3043      pDelete(&(temp1->m[i]));
3044    }
3045    else
3046    {
3047      pShift(&(temp1->m[i]),-length);
3048    }
3049  }
3050  idSkipZeroes(temp1);
3051  temp1->rank = rk;
3052  return temp1;
3053}
3054
3055int idElem(ideal F)
3056{
3057  int i=0,j=0;
3058
3059  while(j<IDELEMS(F))
3060  {
3061   if ((F->m)[j]!=NULL) i++;
3062   j++;
3063  }
3064  return i;
3065}
3066
3067/*
3068*computes module-weights for liftings of homogeneous modules
3069*/
3070intvec * idMWLift(ideal mod,intvec * weights)
3071{
3072  if (idIs0(mod)) return new intvec(2);
3073  int i=IDELEMS(mod);
3074  while ((i>0) && (mod->m[i-1]==NULL)) i--;
3075  intvec *result = new intvec(i+1);
3076  while (i>0)
3077  {
3078    (*result)[i]=pFDeg(mod->m[i])+(*weights)[pGetComp(mod->m[i])];
3079  }
3080  return result;
3081}
3082
3083/*2
3084*sorts the kbase for idCoef* in a special way (lexicographically
3085*with x_max,...,x_1)
3086*/
3087ideal idCreateSpecialKbase(ideal kBase,intvec ** convert)
3088{
3089  int i;
3090  ideal result;
3091
3092  if (idIs0(kBase)) return NULL;
3093  result = idInit(IDELEMS(kBase),kBase->rank);
3094  *convert = idSort(kBase,FALSE);
3095  for (i=0;i<(*convert)->length();i++)
3096  {
3097    result->m[i] = pCopy(kBase->m[(**convert)[i]-1]);
3098  }
3099  return result;
3100}
3101
3102/*2
3103*returns the index of a given monom in the list of the special kbase
3104*/
3105int idIndexOfKBase(poly monom, ideal kbase)
3106{
3107  int j=IDELEMS(kbase);
3108
3109  while ((j>0) && (kbase->m[j-1]==NULL)) j--;
3110  if (j==0) return -1;
3111  int i=pVariables;
3112  while (i>0)
3113  {
3114    loop
3115    {
3116      if (pGetExp(monom,i)>pGetExp(kbase->m[j-1],i)) return -1;
3117      if (pGetExp(monom,i)==pGetExp(kbase->m[j-1],i)) break;
3118      j--;
3119      if (j==0) return -1;
3120    }
3121    if (i==1)
3122    {
3123      while(j>0)
3124      {
3125        if (pGetComp(monom)==pGetComp(kbase->m[j-1])) return j-1;
3126        if (pGetComp(monom)>pGetComp(kbase->m[j-1])) return -1;
3127        j--;
3128      }
3129    }
3130    i--;
3131  }
3132  return -1;
3133}
3134
3135/*2
3136*decomposes the monom in a part of coefficients described by the
3137*complement of how and a monom in variables occuring in how, the
3138*index of which in kbase is returned as integer pos (-1 if it don't
3139*exists)
3140*/
3141poly idDecompose(poly monom, poly how, ideal kbase, int * pos)
3142{
3143  int i;
3144  poly coeff=pOne(), base=pOne();
3145
3146  for (i=1;i<=pVariables;i++)
3147  {
3148    if (pGetExp(how,i)>0)
3149    {
3150      pSetExp(base,i,pGetExp(monom,i));
3151    }
3152    else
3153    {
3154      pSetExp(coeff,i,pGetExp(monom,i));
3155    }
3156  }
3157  pSetComp(base,pGetComp(monom));
3158  pSetm(base);
3159  pSetCoeff(coeff,nCopy(pGetCoeff(monom)));
3160  pSetm(coeff);
3161  *pos = idIndexOfKBase(base,kbase);
3162  if (*pos<0)
3163    pDelete(&coeff);
3164  pDelete(&base);
3165  return coeff;
3166}
3167
3168/*2
3169*returns a matrix A of coefficients with kbase*A=arg
3170*if all monomials in variables of how occur in kbase
3171*the other are deleted
3172*/
3173matrix idCoeffOfKBase(ideal arg, ideal kbase, poly how)
3174{
3175  matrix result;
3176  ideal tempKbase;
3177  poly p,q;
3178  intvec * convert;
3179  int i=IDELEMS(kbase),j=IDELEMS(arg),k,pos;
3180#if 0
3181  while ((i>0) && (kbase->m[i-1]==NULL)) i--;
3182  if (idIs0(arg))
3183    return mpNew(i,1);
3184  while ((j>0) && (arg->m[j-1]==NULL)) j--;
3185  result = mpNew(i,j);
3186#else
3187  result = mpNew(i, j);
3188  while ((j>0) && (arg->m[j-1]==NULL)) j--;
3189#endif
3190
3191  tempKbase = idCreateSpecialKbase(kbase,&convert);
3192  for (k=0;k<j;k++)
3193  {
3194    p = arg->m[k];
3195    while (p!=NULL)
3196    {
3197      q = idDecompose(p,how,tempKbase,&pos);
3198      if (pos>=0)
3199      {
3200        MATELEM(result,(*convert)[pos],k+1) =
3201            pAdd(MATELEM(result,(*convert)[pos],k+1),q);
3202      }
3203      else
3204        pDelete(&q);
3205      pIter(p);
3206    }
3207  }
3208  idDelete(&tempKbase);
3209  return result;
3210}
3211
3212intvec * idQHomWeights(ideal id)
3213{
3214  intvec * imat=new intvec(2*pVariables,pVariables,0);
3215  poly actHead=NULL,wPoint=NULL;
3216  int actIndex,i=-1,j=1,k;
3217  BOOLEAN notReady=TRUE;
3218
3219  while (notReady)
3220  {
3221    if (wPoint==NULL)
3222    {
3223      i++;
3224      while ((i<IDELEMS(id))
3225      && ((id->m[i]==NULL) || (pNext(id->m[i])==NULL)))
3226        i++;
3227      if (i<IDELEMS(id))
3228      {
3229        actHead = id->m[i];
3230        wPoint = pNext(actHead);
3231      }
3232    }
3233    while ((wPoint!=NULL) && (j<=2*pVariables))
3234    {
3235      for (k=1;k<=pVariables;k++)
3236        IMATELEM(*imat,j,k) += pGetExp(actHead,k)-pGetExp(wPoint,k);
3237      pIter(wPoint);
3238      j++;
3239    }
3240    if ((i>=IDELEMS(id)) || (j>2*pVariables))
3241    {
3242      ivTriangMat(imat,1,1);
3243      j = ivFirstEmptyRow(imat);
3244      if ((i>=IDELEMS(id)) || (j>pVariables)) notReady=FALSE;
3245    }
3246  }
3247  intvec *result=NULL;
3248  if (j<=pVariables)
3249  {
3250    result=ivSolveIntMat(imat);
3251  }
3252  //else
3253  //{
3254  //  WerrorS("not homogeneous");
3255  //}
3256  delete imat;
3257  return result;
3258}
3259
3260/*2
3261* returns the presentation of an isomorphic, minimally
3262* embedded  module
3263*/
3264ideal idMinEmbedding(ideal arg)
3265{
3266  if (idIs0(arg)) return idInit(1,arg->rank);
3267
3268  int i,j,k,pC;
3269  poly p,q;
3270  int rg=arg->rank;
3271  ideal res = idCopy(arg);
3272  intvec *indexMap=new intvec(rg+1);
3273  intvec *toKill=new intvec(rg+1);
3274
3275  loop
3276  {
3277    k = 0;
3278    for (i=indexMap->length()-1;i>0;i--)
3279    {
3280      (*indexMap)[i] = i;
3281      (*toKill)[i] = 0;
3282    }
3283    for (j=IDELEMS(res)-1;j>=0;j--)
3284    {
3285      if ((res->m[j]!=NULL) && (pIsConstantComp(res->m[j])) &&
3286           (pNext(res->m[j])==NULL))
3287      {
3288        pC = pGetComp(res->m[j]);
3289        if ((*toKill)[pC]==0)
3290        {
3291          rg--;
3292          (*toKill)[pC] = 1;
3293          for (i=indexMap->length()-1;i>=pC;i--)
3294            (*indexMap)[i]--;
3295        }
3296        pDelete(&(res->m[j]));
3297        k++;
3298      }
3299    }
3300    idSkipZeroes(res);
3301    if (k==0) break;
3302    if (rg>0)
3303    {
3304      res->rank=rg;
3305      for (j=IDELEMS(res)-1;j>=0;j--)
3306      {
3307        while ((res->m[j]!=NULL) && ((*toKill)[pGetComp(res->m[j])]==1))
3308          pDelete1(&res->m[j]);
3309        p = res->m[j];
3310        while ((p!=NULL) && (pNext(p)!=NULL))
3311        {
3312          pSetComp(p,(*indexMap)[pGetComp(p)]);
3313          while ((pNext(p)!=NULL) && ((*toKill)[pGetComp(pNext(p))]==1))
3314            pDelete1(&pNext(p));
3315          pIter(p);
3316        }
3317        if (p!=NULL) pSetComp(p,(*indexMap)[pGetComp(p)]);
3318      }
3319      idSkipZeroes(res);
3320    }
3321    else
3322    {
3323      idDelete(&res);
3324      res=idFreeModule(1);
3325      break;
3326    }
3327  }
3328  delete toKill;
3329  delete indexMap;
3330  return res;
3331}
3332
3333/*2
3334* transpose a module
3335*/
3336ideal idTransp(ideal a)
3337{
3338  int r = a->rank, c = IDELEMS(a);
3339  ideal b =  idInit(r,c);
3340
3341  for (int i=c; i>0; i--)
3342  {
3343    poly p=a->m[i-1];
3344    while(p!=NULL)
3345    {
3346      poly h=pHead(p);
3347      int co=pGetComp(h)-1;
3348      pSetComp(h,i);
3349      b->m[co]=pAdd(b->m[co],h);
3350      pIter(p);
3351    }
3352  }
3353  return b;
3354}
3355
Note: See TracBrowser for help on using the repository browser.