source: git/Singular/LIB/normaliz.lib @ a1b6c91

spielwiese
Last change on this file since a1b6c91 was a1b6c91, checked in by Hans Schoenemann <hannes@…>, 8 years ago
typo
  • Property mode set to 100644
File size: 53.1 KB
Line 
1//// Singular library normaliz.lib
2
3version="version normaliz.lib 4.0.2.1 Sept_2015 "; // $Id$
4category="Commutative Algebra";
5info="
6LIBRARY: normaliz.lib  Provides an interface for the use of Normaliz 2.11 or
7         newer within SINGULAR.
8AUTHORS: Winfried Bruns, Winfried.Bruns@Uni-Osnabrueck.de
9         Christof Soeger, Christof.Soeger@Uni-Osnabrueck.de
10
11OVERVIEW:
12@texinfo
13The library normaliz.lib provides an interface for the use of Normaliz 2.11 or
14newer within SINGULAR. The exchange of data is via files.
15In addition to the top level
16functions that aim at objects of type ideal or ring, several other auxiliary
17functions allow the user to apply Normaliz to data of type intmat. Therefore
18SINGULAR can be used as a comfortable environment for the work with Normaliz.
19@* Please see the @code{Normaliz.pdf} (included in the Normaliz
20distribution) for a more extensive documentation of Normaliz.
21
22Normaliz allows the use of a grading. In the Singular functions that access
23Normaliz the parameter grading is an intvec that assigns a (not necessarily
24positive) degree to every variable of the ambient polynomial ring.
25But it must give positive degrees to the generators given to function.
26
27Singular and Normaliz exchange data via files. These files are automatically
28created and erased behind the scenes. As long as one wants to use only the
29ring-theoretic functions there is no need for file management.
30@*Note that the numerical invariants computed by Normaliz can be
31accessed in this \"automatic file mode\".
32@*However, if Singular is used as a frontend for Normaliz or the user
33wants to inspect data not automatically returned to Singular, then
34an explicit filename and a path can be specified for the exchange of
35data. Moreover, the library provides functions for access to these files.
36Deletion of the files is left to the user.
37
38Use of this library requires the program Normaliz to be installed.
39You can download it from
40@uref{http://www.mathematik.uni-osnabrueck.de/normaliz/}. Please make sure
41that the executables are in the search path or use setNmzExecPath
42(@ref{setNmzExecPath}).
43@end texinfo
44
45KEYWORDS: integral closure; normalization; toric ring
46
47PROCEDURES:
48 intclToricRing(ideal I)      computes the integral closure of the toric ring
49                              generated by the leading monomials of the
50                              elements of I in the basering
51 normalToricRing(ideal I)     computes the normalization of the toric ring
52                              generated by the leading monomials of the
53                              elements of I
54 normalToricRingFromBinomials(ideal I)  computes the normalization of the
55                              polynomial ring modulo the unique minimal binomial
56                              prime ideal of the binomial ideal I
57 ehrhartRing(ideal I)         considers the exponent vectors of the elements of I
58                              as points of a lattice polytope and computes the
59                              integral cloure of the polytopal algebra
60 intclMonIdeal(ideal I)       Computes the integral closure of the Rees algebra
61                              of the ideal generated by the leading monomials of
62                              the elements of I
63 torusInvariants(intmat T)    computes the ring of invariants of a torus action
64 finiteDiagInvariants(intmat C)  computes the ring of invariants of a finite
65                                 abelian group acting diagonally on a polynomial
66                                 ring
67 diagInvariants(intmat C)     computes the ring of invariants of a
68                              diagonalizable group
69 intersectionValRings(intmat V)   computes the intersection of the polynomial
70                                  ring with the valuation rings of monomial
71                                  valuations
72 intersectionValRingIdeals(intmat V)       computes ideals of monomial valuations
73
74 showNuminvs()                prints the numerical invariants found by Normaliz
75 exportNuminvs()              exports the numerical invariants found by Normaliz
76
77 setNmzOption(string s, int onoff) sets the option s to onoff
78 showNmzOptions()             prints the enabled options to the standard output
79
80 normaliz(intmat sgr,int nmz_mode) applies Normaliz
81 setNmzExecPath(string nmz_exec_path_name) sets the path to the Normaliz
82                                           executable
83
84 writeNmzData(intmat sgr, int n_mode) creates an input file for Normaliz
85 readNmzData(string nmz_suffix) reads the Normaliz output file with the
86                                specified suffix
87
88 setNmzFilename(string nmz_filename_name) sets the filename for the exchange
89                                          of data
90 setNmzDataPath(string nmz_data_path_name) sets the directory for the exchange
91                                           of data
92 writeNmzPaths()              writes the path names into two files
93 startNmz()                   retrieves the path names written by writeNmzPaths
94 rmNmzFiles()                 removes the files created for and by Normaliz
95
96 mons2intmat(ideal I)         returns the intmat whose rows represent the
97                              leading exponents of the elements of I
98 intmat2mons(intmat expo_vecs) returns the ideal generated by the monomials
99                               which have the rows of expo_vecs as
100                               exponent vector
101 binomials2intmat(ideal I)    returns the intmat whose rows represent the
102                              exponents of the elements of the binomial ideal I
103";
104
105
106// helpers
107
108static proc desInt(string intname, int value)
109// define, export and set an integer
110{
111    int exists;
112    if(defined(`intname`)){exists=1;}
113    if(!exists)
114    {
115        int `intname`=value;export(`intname`);
116    }
117    `intname`=value;
118}
119
120static proc desString(string stringname, string value)
121// define, export and set a string
122{
123    int exists;
124    if(defined(`stringname`)){exists=1;}
125    if(!exists)
126    {
127        string `stringname`=value;export(`stringname`);
128    }
129    `stringname`=value;
130}
131
132static proc queryInt(string intname)
133// if intname is defined, return(intname), else return(0)
134{
135    int exists,value;
136    if(defined(`intname`)){exists=1;}
137    if(!exists)
138    {
139        return(0);
140    }
141    return(`intname`);
142}
143
144static proc queryString(string stringname)
145// if stringname is defined, return(stringname), else return("")
146{
147    int exists;
148    string value;
149    if(defined(`stringname`)){exists=1;}
150    if(!exists)
151    {
152        return("");
153    }
154    return(`stringname`);
155}
156
157static proc fileExists(string f)
158{
159    return(status (f,"exists")=="yes");
160}
161
162static proc appendSlash(string s)
163// if nonempty and / is not the terminating char
164{
165    if(size(s)>0)
166    {
167        if(s[size(s)]!="/")
168        {
169            s=s+"/";
170            return(s);
171        }
172    }
173    return(s);
174}
175
176// filenames and paths
177
178proc setNmzExecPath(string nmz_exec_path_name)
179"USAGE:   setNmzExecPath(string s);   @code{s} path to the Normaliz executable
180CREATE:   @code{Normaliz::nmz_exec_path} to save the given path @code{s}
181NOTE:     It is not necessary to use this function if the Normaliz executable
182          is in the search path of the system.
183SEE ALSO: setNmzOption
184EXAMPLE:  example setNmzExecPath; shows an example"
185{
186    desString("nmz_exec_path",nmz_exec_path_name);
187    nmz_exec_path=appendSlash(nmz_exec_path);
188}
189example
190{ "EXAMPLE:";echo = 2;
191  setNmzExecPath("../Normaliz/");
192}
193
194proc setNmzFilename(string nmz_filename_name)
195"USAGE:   setNmzFilename(string s);
196CREATE:   @code{Normaliz::nmz_filename} to save the given filename @code{s}
197NOTE:     The function sets the filename for the exchange of data. Unless a
198          path is set by setNmzDataPath, files will be created in the current
199          directory.
200          @* If a non-empty filename is set, the files created for and by
201             Normaliz are kept. This is mandatory for the data access functions
202             (see @ref{writeNmzData} and @ref{readNmzData}).
203          @* Resetting the filename by setNmzFilename(\"\") forces the library
204             to return to deletion of temporary files, but the files created
205             while the filename had been set will not be erased.
206SEE ALSO: writeNmzData, readNmzData, setNmzDataPath, rmNmzFiles
207EXAMPLE:  example setNmzFilename; shows an example"
208{
209    desString("nmz_filename",nmz_filename_name);
210    if(nmz_filename_name!="")
211    {
212        desInt("nmz_files_keep_switch",1);
213    }
214    else
215    {
216        desInt("nmz_files_keep_switch",0);
217    }
218}
219example
220{ "EXAMPLE:";echo = 2;
221  setNmzDataPath("examples/");
222  setNmzFilename("example1");
223  //now the files for the exchange with Normaliz are examples/example1.SUFFIX
224}
225
226proc setNmzDataPath(string nmz_data_path_name)
227"USAGE:   setNmzDataPath(string s);
228CREATE:   @code{Normaliz::nmz_data_path} to save the given path @code{s}
229NOTE:     The function sets the path for the exchange of data. By default the
230          files will be created in the current directory.
231          @* It seems that Singular cannot use filenames starting with @code{~}
232             or @code{$HOME} in its input/output functions.
233          @* You must also avoid path names starting with @code{/} if you work
234             under Cygwin, since Singular and Normaliz interpret them in
235             different ways.
236SEE ALSO: writeNmzData, readNmzData, rmNmzFiles, setNmzFilename
237EXAMPLE:  example setNmzDataPath; shows an example"
238{
239    desString("nmz_data_path",nmz_data_path_name);
240    nmz_data_path=appendSlash(nmz_data_path);
241}
242example
243{ "EXAMPLE:";echo = 2;
244  setNmzDataPath("examples/");
245  setNmzFilename("example1");
246  //now the files for the exchange with Normalize are examples/example1.SUFFIX
247}
248
249proc writeNmzPaths();
250"USAGE:   writeNmzPaths();
251CREATE:   the file nmz_sing_exec.path where the path to the Normaliz executable
252          is saved
253          @* the file nmz_sing_data.path where the directory for the exchange
254          of data is saved
255NOTE:     Both files are saved in the current directory. If one of the names
256          has not been defined, the corresponding file is created, but
257          contains nothing.
258SEE ALSO: setNmzDataPath, setNmzExecPath, startNmz
259EXAMPLE:  example writeNmzPaths; shows an example
260"{
261    link outf=":w nmz_sing_exec.path";
262    write(outf, queryString("nmz_exec_path"));
263    close(outf);
264
265    outf=":w nmz_sing_data.path";
266    write(outf, queryString("nmz_data_path"));
267    close(outf);
268}
269example
270{ "EXAMPLE:";echo = 2;
271  setNmzExecPath("../Normaliz/");
272  writeNmzPaths();
273  int dummy=system("sh","cat nmz_sing_exec.path");
274  dummy=system("sh","cat nmz_sing_data.path");
275}
276
277proc startNmz()
278"USAGE:   startNmz();
279PURPOSE:  This function reads the files written by @code{writeNmzPaths()},
280          retrieves the path names, and types them on the standard output
281          (as far as they have been set). Thus, once the path names have been
282          stored, a Normaliz session can simply be opened by this function.
283SEE ALSO: setNmzDataPath, setNmzExecPath, writeNmzPaths
284EXAMPLE:  example startNmz; shows an example
285"
286{
287    link inf=":r nmz_sing_exec.path";
288    string s=read(inf);
289    int i,p;
290    p=findWord("/",s,1);
291    if(p!=-1)
292    {
293        for(i=size(s);i>=1;i--)
294        {
295            if(s[i]=="/")
296            {
297                s=s[1..i];
298                break;
299            }
300        }
301        desString("nmz_exec_path",s);
302        "nmz_exec_path is",nmz_exec_path;
303    }
304    else
305    {
306        "nmz_exec_path not set";
307    }
308
309    inf=":r nmz_sing_data.path";
310    s=read(inf);
311    p=findWord("/",s,1);
312    if(p!=-1)
313    {
314        for(i=size(s);i>=1;i--)
315        {
316            if(s[i]=="/")
317            {
318                s=s[1..i];
319                break;
320            }
321        }
322        desString("nmz_data_path",s);
323        "nmz_data_path is",nmz_data_path;
324    }
325    else
326    {
327        "nmz_data_path not set";
328    }
329}
330example
331{ "EXAMPLE:"; echo=2;
332  startNmz();
333}
334
335static proc getNmzFile()
336{
337    if(queryInt("nmz_files_keep_switch"))
338    {
339        return(queryString("nmz_data_path")+queryString("nmz_filename"));
340    }
341    else
342    {
343        return(queryString("nmz_filename"));
344    }
345}
346
347static proc makeTempNmzDataPath()
348{
349    string testdir, testdir1;
350    int i,dummy;
351
352    testdir1="/tmp/nmz_sing_"+string(system("pid"));
353    testdir=testdir1;
354    while(fileExists(testdir))
355    {
356        i++;
357        testdir=testdir1+string(i);
358    }
359    dummy=system("sh","mkdir "+ testdir);
360    desString("nmz_filename",testdir+"/nmz"); //files are nmz+suffix in testdir
361}
362
363static proc eraseTempNmzDataPath();
364{
365    int dummy;
366
367    string tmpdir=getNmzFile();
368    tmpdir=tmpdir[1..size(tmpdir)-4]; // remove "/nmz"
369    dummy=system("sh","rm -r "+tmpdir);
370    setNmzFilename("");
371}
372
373static proc setNmzExec()
374{
375    return(queryString("nmz_exec_path")+"normaliz");
376}
377
378proc rmNmzFiles()
379"USAGE:  rmNmzFiles();
380PURPOSE: This function removes the files created for and by Normaliz, using
381         the last filename specified.
382         It needs an explicit filename set (see @ref{setNmzFilename}).
383SEE ALSO: writeNmzData, readNmzData, setNmzFilename, setNmzDataPath
384EXAMPLE:  example rmNmzFiles; shows an example
385"{
386
387    if(!queryInt("nmz_files_keep_switch"))
388    {
389        ERROR("rmNmzFiles: no filename specified");
390    }
391
392    list suffixes="in","gen","out","cst","typ","egn","esp","inv","tri","ht1",
393                  "ext","dec", "lat", "mod";
394    int i,dummy;
395    string f;
396
397    for(i=1;i<=size(suffixes);i++)
398    {
399        f=getNmzFile()+"."+suffixes[i];
400        if (fileExists(f))
401        {
402            dummy=system("sh","rm "+f+ "&> /dev/null");
403        }
404    }
405}
406example
407{ "EXAMPLE:"; echo=2;
408  setNmzFilename("VeryInteresting");
409  rmNmzFiles();
410}
411
412
413
414// parsing normaliz output
415
416static proc digit(string s)
417{
418    if(s==" ") // skip blanks quickly
419    {
420        return(0);
421    }
422
423    if((s[1]>="0" && s[1]<="9")||s[1]=="-")
424    {
425        return(1);
426    }
427    return(0);
428}
429
430static proc nextWord(string s, int p)
431{
432    int j,sw,ew;
433
434    for(;p<=size(s);p++) // must start with a letter
435    {
436
437        if((s[p]>="a" && s[p]<="z")||
438             (s[p]>="A" && s[p]<="Z"))
439        {
440            sw=p; break;
441        }
442    }
443    if(p>size(s))
444    {
445        return(-1,-1); // no word found
446    }
447
448    for(;p<=size(s);p++) // now numerals and -_ allowed
449    {
450        if(!((s[p]>="a" && s[p]<="z")||
451             (s[p]>="A" && s[p]<="Z")||
452             (s[p]>="0" && s[p]<="9")||
453              s[p]=="_"||s[p]=="-"))
454        {
455            break;
456        }
457    }
458    return(sw,p);
459}
460
461static proc getInt(string s, int p)
462{
463    string nst;
464    int i,j,en,sn;
465
466    for(;p<=size(s);p++)
467    {
468
469        if(digit(s[p]))
470        {
471            sn=p; break;
472        }
473    }
474    if(not(sn))
475    {
476        return(0,-1); // -1 indicates: no number found
477    }
478    p++;
479    for(;p<=size(s);p++)
480    {
481        if(!digit(s[p]))
482        {
483            en=p-1; break;
484        }
485    }
486    if(p>size(s))
487    {
488        en=size(s);
489    }
490    nst="i="+s[sn,en-sn+1];
491    execute(nst);
492    return(i,p);
493}
494
495
496static proc getRational(string s, int p)
497{
498    string nst;
499    int i,j,en,sn;
500
501    for(;p<=size(s);p++)
502    {
503        if(digit(s[p]))
504        {
505            sn=p; break;
506        }
507    }
508    if(not(sn))
509    {
510        return(0,-1); // -1 indicates: no number found
511    }
512    p++;
513    int slash_at;
514    for(;p<=size(s);p++)
515    {
516        if(s[p]=="/")
517        {
518            slash_at=p;
519            p++;
520            continue;
521        }
522        if(!digit(s[p]))
523        {
524            en=p-1; break;
525        }
526    }
527    if(p>size(s))
528    {
529        en=size(s);
530    }
531    if(slash_at)
532    {
533        nst="i="+s[sn,slash_at-sn];
534        execute(nst);
535        nst="j="+s[slash_at+1,en-slash_at];
536        execute(nst);
537        return(i,p,j);
538    }
539    nst="i="+s[sn,en-sn+1];
540    execute(nst);
541    return(i,p);
542}
543
544
545static proc findWord(string s, string t, int p)
546{
547    for(;p<=size(t)-size(s)+1;p++)
548    {
549        if(t[p]==s[1])
550        {
551            if(t[p,size(s)]==s)
552            {
553                 return(p+size(s));
554            }
555        }
556    }
557    return(-1);
558}
559
560
561static proc skipEqualsign(string s,int p)
562{
563    for(;p<=size(s);p++)
564    {
565        if(s[p]=="=")
566        {
567            break;
568        }
569    }
570    return(p+1);
571}
572
573
574// input and output to/from normaliz
575
576//list must have pairs of intmat, nmz_mode
577static proc doWriteNmzData(list #)
578{
579    string s;
580    int i,j;
581    link outf=":w "+ getNmzFile() +".in";  // also sets the filename
582
583    intmat sgr;
584    int num_rows, num_cols, n_mode;
585
586    for (int k=1; k+1<=size(#); k=k+2) {
587    //get data from the parameter list
588        n_mode   = #[k+1];
589        if (n_mode != -1) { //skip -1 mode
590            sgr = #[k];
591            num_rows = nrows(sgr);
592            num_cols = ncols(sgr);
593
594            write(outf,num_rows);
595            write(outf,num_cols);
596
597            for(i=1;i<=nrows(sgr);i++)
598            {
599                s="";
600                for(j=1;j<=num_cols;j++)
601                {
602                    s=s+string(sgr[i,j])+" ";
603                }
604                write(outf,s);
605            }
606            if (n_mode == 20) {
607                write(outf,"grading");}
608            if (n_mode == 0) {
609                write(outf,"integral_closure");}
610            if (n_mode == 1) {
611                write(outf,"normalization");}
612            if (n_mode == 2) {
613                write(outf,"polytope");}
614            if (n_mode == 3) {
615                write(outf,"rees_algebra");}
616            if (n_mode == 4) {
617                write(outf,"inequalities");}
618            if (n_mode == 5) {
619                write(outf,"equations");}
620            if (n_mode == 6) {
621                write(outf,"congruences");}
622            if (n_mode == 10) {
623                write(outf,"lattice_ideal");}
624            write(outf,"");
625        }
626    }
627    close(outf);
628}
629
630
631static proc prepareGrading(list #)
632{
633    if (size(#)==0) {
634        return(0,-1); // mode -1 specifies discard the matrix
635    }
636    if (size(#)>1) {
637        print(#);
638        ERROR("To many parameters!");
639    }
640    intmat g = intmat(#[1],1,size(#[1]));
641    return (g,20);
642}
643
644
645proc writeNmzData(intmat sgr, int n_mode, list #)
646"USAGE:   writeNmzData(intmat M, int mode);
647          writeNmzData(intmat M, int mode, intmat M2, int mode2, ...);
648CREATE:   Creates an input file for Normaliz from the matrix M. The second
649          parameter sets the mode. How the matrix is interpreted depends on the
650          mode. See the Normaliz documentation for more information.
651
652          It is also possible to give more than one pair of matrix and mode. In
653          this case all matrices and modes are written. This can be used to
654          combine modes 4,5,6.
655          Use mode=20 to specify a grading.
656NOTE:     Needs an explicit filename set. The filename is created from the
657          current filename.
658   @*     Note that all functions in normaliz.lib write and read their data
659          automatically to and from the hard disk so that writeNmzData will
660          hardly ever be used explicitly.
661SEE ALSO: readNmzData, rmNmzFiles, setNmzFilename, setNmzDataPath
662EXAMPLE:  example writeNmzData; shows an example"
663{
664    if(queryString("nmz_filename")=="")
665    {
666        ERROR("writeNmzData: no filename specified");
667    }
668    doWriteNmzData(list(sgr, n_mode) + #);
669}
670example
671{ "EXAMPLE:"; echo=2;
672  setNmzFilename("VeryInteresting");
673  intmat sgr[3][3]=1,2,3,4,5,6,7,8,10;
674  writeNmzData(sgr,1);
675  int dummy=system("sh","cat VeryInteresting.in");
676
677  intmat Hyperplanes[2][3] = 2,-1,0, // 2x-y >= 0
678                             1, 1,0; //  x+y >= 0
679  intmat Equation[1][3] = 0,1,-1;    // y = z
680  intmat Congruence[1][4] = 1,0,0,3;  // x = 0 (3)
681  writeNmzData(Hyperplanes,4,Equation,5,Congruence,6);
682  dummy=system("sh","cat VeryInteresting.in");
683}
684
685
686proc readNmzData(string nmz_suffix)
687"USAGE:  readNmzData(string suffix);
688RETURN:  Reads an output file of Normaliz containing an integer matrix and
689         returns it as an intmat. For example, this function is useful if one
690         wants to inspect the support hyperplanes. The filename is created
691         from the current  filename and the suffix given to the function.
692NOTE:    Needs an explicit filename set by setNmzFilename.
693   @*    Note that all functions in normaliz.lib write and read their data
694         automatically so that readNmzData will usually not be used explicitly.
695   @*    This function reads only the first matrix in a file!
696SEE ALSO: writeNmzData, rmNmzFiles, setNmzFilename, setNmzDataPath
697EXAMPLE:  example readNmzData; shows an example"
698{
699    if(queryString("nmz_filename")=="")
700    {
701        ERROR("readNmzData: no filename specified");
702    }
703
704    string s;
705    int n_rows,n_cols;            //number of rows/columns
706    int p;                     //position
707    int i,j;
708    int returnvalue;
709
710    string filename = getNmzFile() + "."+ nmz_suffix;
711    link in_f=":r "+ filename;
712    s=read(in_f);
713    close(in_f);
714
715    p=1;
716    (n_rows,p)=getInt(s,p);
717    (n_cols,p)=getInt(s,p);
718    if (n_rows <= 0 || n_cols <= 0) {
719         intmat empty;
720         return(empty);
721    }
722    intmat nmz_gen[n_rows][n_cols];
723    for(i=1;i<=n_rows;i++)
724    {
725        for(j=1;j<=n_cols;j++)
726        {
727            (nmz_gen[i,j],p) = getInt(s,p);
728        }
729    }
730    return(nmz_gen);
731}
732example
733{ "EXAMPLE:"; echo=2;
734  setNmzFilename("VeryInteresting");
735  intmat sgr[3][3]=1,2,3,4,5,6,7,8,10;
736  intmat sgrnormal=normaliz(sgr,0);
737  readNmzData("cst");
738}
739
740
741// running normaliz (with options)
742
743// component 1 is name of option
744// 2 is default value
745// 3 is command line option to be passed to Normaliz
746// 4 indictes whether file "gen" is generated
747// value 2 of 4 indicates "no influence"
748
749static proc defNmzOptions()
750{
751    if(!defined(nmz_options)) // can be defined only once
752    {
753        list nmz_options=
754        list("supp",0,"-s",0),
755        list("triang",0,"-tT",0),
756        list("volume",0,"-v",0),
757        list("hvect",0,"-p",0),
758        list("height1",0,"-1",0),
759        list("normal",0,"-n",1),
760        list("normal_l",0,"-N",1),
761        list("hilb",0,"-h",1),
762        list("dual",0,"-d",1),
763        list("control",0,"-c",2),
764        list("allf",0,"-a",2),
765        list("errorcheck",0,"-e",2),
766        list("bigint",0,"-B",2),
767        list("threads",0,"-x=",2);
768        export(nmz_options);
769    }
770}
771
772proc setNmzOption(string s, int onoff)
773"USAGE:   setNmzOption(string s, int onoff);
774PURPOSE:  If @code{onoff=1} the option @code{s} is activated, and
775          if @code{onoff=0} it is deactivated.
776The Normaliz options are accessible via the following names:
777@* @code{-s:  supp}
778@* @code{-t:  triang}
779@* @code{-v:  volume}
780@* @code{-p:  hvect}
781@* @code{-1:  height1}
782@* @code{-n:  normal}
783@* @code{-N:  normal_l}
784@* @code{-h:  hilb}
785@* @code{-d:  dual}
786@* @code{-a:  allf}
787@* @code{-c:  control}
788@* @code{-e:  errorcheck}
789@* @code{-B:  bigint} Use GMP for arbitrary precision integers
790@* @code{-x=N:  threads} In this case the int parameter is used to set the
791                         number of threads N, 0 means no explicit limiting.
792
793            In the next version of this library the options will be accessible
794            via their standard Normaliz 3.0 names.
795
796SEE ALSO: showNmzOptions
797EXAMPLE:  example setNmzOption; shows an example
798"
799{
800    defNmzOptions();
801    for(int i=1;i<=size(nmz_options);i++)
802    {
803        if(s==nmz_options[i][1])
804        {
805            nmz_options[i][2]=onoff;
806            return(1);
807        }
808    }
809    "Invalid option ", s;
810    return(0);
811}
812example
813{ "EXAMPLE:"; echo=2;
814  setNmzOption("hilb",1);
815  showNmzOptions();
816}
817
818static proc collectNmzOptions()
819{
820    defNmzOptions();
821    string run_options=" -f ";
822    desInt("GenGen",1); // indicates whether "gen" is generated
823    for(int i=1;i<=size(nmz_options);i++)
824    {
825        if(nmz_options[i][2])
826        {
827            run_options=run_options+nmz_options[i][3];
828                if (nmz_options[i][1]=="threads") {
829                    run_options=run_options+string(nmz_options[i][2]);
830                }
831                run_options=run_options+" ";
832            if(nmz_options[i][4]!=2)
833            {
834                GenGen=nmz_options[i][4];
835            }
836        }
837    }
838    return(run_options+" ");
839}
840
841proc showNmzOptions()
842"USAGE:   showNmzOptions();
843RETURN:   Returns the string of activated options.
844NOTE:     This string is used as parameter when calling Normaliz.
845SEE ALSO: setNmzOption
846EXAMPLE:  example showNmzOption; shows an example
847"
848{
849    return(collectNmzOptions());
850}
851example
852{ "EXAMPLE:"; echo=2;
853  setNmzOption("hilb",1);
854  showNmzOptions();
855}
856
857
858static proc runNormaliz(intmat sgr, int nmz_mode, list #)
859{
860    if(!queryInt("nmz_files_keep_switch"))
861    {
862        makeTempNmzDataPath();
863    }
864
865    doWriteNmzData(list(sgr, nmz_mode) + #);
866
867    if(queryInt("nmz_files_keep_switch"))
868    {
869       int dummy=system("sh",setNmzExec()+ collectNmzOptions() + getNmzFile());
870    }
871    else
872    {
873        string gotodir="/tmp";
874        string fname=getNmzFile();
875        fname=fname[6..size(fname)];
876        string exec="cd "+gotodir+" ; ";
877        exec=exec+setNmzExec()+ collectNmzOptions()+" ";
878        exec=exec+fname+" ;";
879        int dummy=system("sh",exec);
880    }
881
882    if(!GenGen) // return input matrix if "gen" has not been generated
883    {
884        if(!queryInt("nmz_files_keep_switch"))
885        {
886            eraseTempNmzDataPath();
887        }
888        return(sgr);
889    }
890    intmat Gen=readNmzData("gen");
891
892    if(!defined(Num_Invs))
893    {
894        list Num_Invs;
895        export Num_Invs;
896    }
897    Num_Invs=getNuminvs();
898
899    if(!queryInt("nmz_files_keep_switch"))
900    {
901        eraseTempNmzDataPath();
902    }
903
904    return(Gen);
905
906}
907
908proc normaliz(intmat sgr,int nmz_mode, list #)
909"USAGE:   normaliz(intmat sgr,int nmz_mode);
910          normaliz(intmat sgr, int nmz_mode, intmat sgr2, int nmz_mode2, ...);
911RETURN:   The function applies Normaliz to the parameter sgr in the mode set
912          by nmz_mode. The function returns the intmat defined by the file
913          with suffix gen.
914
915          It is also possible to give more than one pair of matrix and mode.
916          In this case all matrices and modes are used.
917
918          In this version one must use the old numerical types of input matrices
919          according to the following table:
920
921@* @code{0:  cone}
922@* @code{1:  cone_and_lattice}
923@* @code{2:  polytope}
924@* @code{3:  rees_algebra}
925@* @code{4:  inequalities}
926@* @code{5:  equations}
927@* @code{6:  congruences}
928@* @code{10:  lattice_ideal}
929@* @code{20:  grading}
930
931          In the next version all input types of Normaliz 3.0 will be accessible
932          via their names. See the Normaliz manual for more information.
933
934NOTE:     You will find procedures for many applications of Normaliz in this
935          library, so the explicit call of this procedure may not be necessary.
936SEE ALSO: intclToricRing, normalToricRing, ehrhartRing, intclMonIdeal,
937          torusInvariants, diagInvariants, finiteDiagInvariants, intersectionValRings,
938             intersectionValRingIdeals
939EXAMPLE:  example normaliz; shows an example
940"
941{
942    return(runNormaliz(sgr,nmz_mode,#));
943}
944example
945{ "EXAMPLE:"; echo=2;
946  ring R=0,(x,y,z),dp;
947  intmat M[3][2]=3,1,
948                 3,2,
949                 1,3;
950  normaliz(M,1);
951
952  intmat Hyperplanes[2][3] = 2,-1,0, // 2x-y >= 0
953                             1, 1,0; //  x+y >= 0
954  intmat Equation[1][3] = 0,1,-1;    // y = z
955  intmat Congruence[1][4] = 1,0,0,3;  // x = 0 (3)
956  normaliz(Hyperplanes,4,Equation,5,Congruence,6);
957}
958
959
960// retrieving normaliz numerical invariants
961
962static proc getNuminvs()
963{
964    string s;
965    list num_invs;
966    int p,sw,v_length,i,dummy_int;
967    intvec dummy_vec;
968    string type_inv,name_inv,dummy_bool;
969
970    link in_f=":r "+ getNmzFile() + "."+"inv";
971    s=read(in_f);
972
973    p=1;
974    while(p<size(s))
975    {
976        (sw,p)=nextWord(s,p);
977        if(sw==-1)
978        {
979            break;
980        }
981        type_inv=s[sw..p-1];
982        if(type_inv=="vector")
983        {
984            (v_length,p)=getInt(s,p);
985            (sw,p)=nextWord(s,p);
986            name_inv=s[sw..p-1];
987            if(name_inv=="h-vector")
988            {
989                name_inv="h_vector";
990            }
991            if(name_inv!="hilbert_polynomial"
992              && name_inv!="hilbert_quasipolynomial")
993            {
994                for(i=1;i<=v_length;i++)
995                {
996                    if(i==1)
997                    {
998                        (dummy_int,p)=getInt(s,p);
999                        dummy_vec=dummy_int;
1000                    }
1001                    else
1002                    {
1003                        (dummy_int,p)=getInt(s,p);
1004                        dummy_vec=dummy_vec,dummy_int;
1005                    }
1006                }
1007                num_invs=num_invs+list(list(name_inv,dummy_vec,"intvec"));
1008            }
1009            else
1010            {
1011                p=skipEqualsign(s,p);
1012            }
1013        }
1014        if(type_inv=="integer")
1015        {
1016            (sw,p)=nextWord(s,p);
1017            name_inv=s[sw..p-1];
1018            if (name_inv!="hilbert_quasipolynomial_denom") {
1019              (dummy_int,p)=getInt(s,p);
1020              num_invs=num_invs+list(list(name_inv,dummy_int,"int"));
1021            }
1022        }
1023        if(type_inv=="boolean")
1024        {
1025            (sw,p)=nextWord(s,p);
1026            name_inv=s[sw..p-1];
1027            p=skipEqualsign(s,p);
1028            (sw,p)=nextWord(s,p);
1029            dummy_bool=s[sw..p-1];
1030            dummy_int=0;
1031            if(dummy_bool=="true")
1032            {
1033                dummy_int=1;
1034            }
1035            num_invs=num_invs+list(list(name_inv,dummy_int,"int"));
1036        }
1037    }
1038    return(num_invs);
1039}
1040
1041proc showNuminvs()
1042"USAGE:   showNuminvs();
1043PURPOSE:  prints the numerical invariants
1044SEE ALSO: exportNuminvs
1045EXAMPLE:  example showNuminvs(); shows an example
1046"
1047{
1048    list dummy;
1049    int i;
1050    for(i=1;i<=size(Num_Invs);i++)
1051    {
1052        dummy=Num_Invs[i];
1053        dummy[1],":", dummy[2];
1054    }
1055}
1056example
1057{ "EXAMPLE:"; echo=2;
1058  ring R=0,(x,y,z,t),dp;
1059  ideal I=x3,x2y,y3;
1060  list l=intclMonIdeal(I);
1061  showNuminvs();
1062}
1063
1064
1065proc exportNuminvs()
1066"USAGE:   exportNuminvs();
1067CREATE:   Creates top-level variables which contain the numerical invariants.
1068          Depending on the options of normaliz different invariants are
1069          calculated. Use showNuminvs (@ref{showNuminvs}) to see which
1070          invariants are available.
1071SEE ALSO: showNuminvs
1072EXAMPLE:  example exportNuminvs; shows an example
1073"
1074{
1075    list dummy;
1076    int i;
1077    string s;
1078    for(i=1;i<=size(Num_Invs);i++)
1079    {
1080        dummy=Num_Invs[i];
1081        s=dummy[3]+" nmz_" + dummy[1] + "=dummy[2]; exportto(Top," + "nmz_" + dummy[1] + ");";
1082        execute(s);
1083    }
1084}
1085example
1086{ "EXAMPLE:"; echo=2;
1087  ring R=0,(x,y,z,t),dp;
1088  ideal I=x3,x2y,y3;
1089  list l=intclMonIdeal(I);
1090  exportNuminvs();
1091  // for example, now the following variables are set:
1092  nmz_hilbert_basis_elements;
1093  nmz_number_extreme_rays;
1094  nmz_rank;
1095  nmz_number_support_hyperplanes;
1096  nmz_multiplicity;
1097  nmz_primary;
1098}
1099
1100
1101// intmats to/from monomials
1102
1103proc mons2intmat(ideal I)
1104"USAGE:   mons2intmat(ideal I);
1105RETURN:   Returns the intmat whose rows represent the leading exponents of the
1106          (non-zero) elements of I. The length of each row is nvars(basering).
1107SEE ALSO: intmat2mons
1108EXAMPLE:  example mons2intmat; shows an example"
1109{
1110    int i,j,k;
1111    intmat expo_vecs[size(I)][nvars(basering)];
1112    intvec expo_v;
1113
1114    k=0;
1115    for(i=1;i<=ncols(I);i++)
1116    {
1117        if(I[i]!=0)
1118        {
1119            k++;
1120            expo_v=leadexp(I[i]);
1121            for(j=1;j<=nvars(basering);j++)
1122            {
1123                expo_vecs[k,j]=expo_v[j];
1124            }
1125        }
1126    }
1127    return(expo_vecs);
1128}
1129example
1130{ "EXAMPLE:"; echo=2;
1131  ring R=0,(x,y,z),dp;
1132  ideal I=x2,y2,x2yz3;
1133  mons2intmat(I);
1134}
1135
1136proc intmat2mons(intmat expo_vecs)
1137"USAGE:   intmat2mons(intmat M);
1138RETURN:   an ideal generated by the monomials which correspond to the exponent
1139          vectors given by the rows of @code{M}
1140NOTE:     The number of variables in the basering @code{nvars(basering)} has to
1141          be at least the number of columns @code{ncols(M)}, otherwise the
1142          function exits with an error.
1143          is thrown (see @ref{ERROR}).
1144SEE ALSO: mons2intmat
1145EXAMPLE:  example intmat2mons; shows an example
1146"
1147{
1148    int i,j;
1149    poly m;
1150    ideal mons;
1151
1152    if(nvars(basering)<ncols(expo_vecs))
1153    {
1154        ERROR("intmat2mons: not enough variables in ring");
1155    }
1156
1157    for(i=1;i<=nrows(expo_vecs);i++)
1158    {
1159        m=1;
1160        for(j=1;j<=ncols(expo_vecs);j++)
1161        {
1162            m=m*var(j)^expo_vecs[i,j];
1163        }
1164        mons=mons,m;
1165    }
1166     mons=simplify(mons,2);    // get rid of starting 0
1167     return(mons);
1168}
1169example
1170{ "EXAMPLE:"; echo=2;
1171  ring R=0,(x,y,z),dp;
1172  intmat expo_vecs[3][3] =
1173  2,0,0,
1174  0,2,0,
1175  2,1,3;
1176  intmat2mons(expo_vecs);
1177}
1178
1179static proc intmat2monsSel(intmat expo_vecs, int d)
1180{
1181    int i,j;
1182    poly m;
1183    ideal mons;
1184
1185    if(nvars(basering)<ncols(expo_vecs)-1)
1186    {
1187        ERROR("intmat2monsSel: not enough variables in ring");
1188    }
1189
1190    for(i=1;i<=nrows(expo_vecs);i++)
1191    {
1192        if(expo_vecs[i,ncols(expo_vecs)]==d)
1193        {
1194            m=1;
1195            for(j=1;j<=ncols(expo_vecs)-1;j++)
1196            {
1197                m=m*var(j)^expo_vecs[i,j];
1198            }
1199            mons=mons,m;
1200        }
1201    }
1202    mons=simplify(mons,2);    // get rid of starting 0
1203    return(mons);
1204}
1205
1206
1207proc binomials2intmat(ideal I)
1208"USAGE:   binomials2intmat(ideal I);
1209RETURN:   Returns the intmat whose rows represent the exponents of the
1210          (non-zero) elements of I which have to be binomials.
1211          The length of each row is nvars(basering).
1212SEE ALSO: mons2intmat, intmat2mons
1213EXAMPLE:  example binomials2intmat; shows an example"
1214{
1215    int i,j,k;
1216    intmat expo_vecs[size(I)][nvars(basering)];
1217    intvec expo_v;
1218
1219    k=0;
1220    poly f;
1221
1222    for(i=1; i<=ncols(I); i++)
1223    {
1224        if( I[i] != 0 )
1225        {
1226            k++;
1227            f = I[i];
1228            if (leadcoef(f) != 1) {f = -f};  //works in all characteristics
1229            if (size(f)!=2 || leadcoef(f)!=1 || leadcoef(f[2])!=-1)
1230            {
1231                ERROR(string("normalToricRing: binomial ideal expected: generator ",i,": ",I[i]));
1232            }
1233
1234            expo_v = leadexp(f)-leadexp(f[2]);
1235            for(j=1;j<=nvars(basering);j++)
1236            {
1237                expo_vecs[k,j]=expo_v[j];
1238            }
1239        }
1240    }
1241    return(expo_vecs);
1242}
1243example
1244{ "EXAMPLE:"; echo=2;
1245  ring S = 37,(u,v,w,x,y,z),dp;
1246  ideal I = u2v-xyz, ux2-vyz, uvw-y2z;
1247  binomials2intmat(I);
1248}
1249
1250
1251// integral closure of rings and ideals
1252
1253static proc runIntclToricRing(ideal I, int nmz_mode, list #)
1254{
1255    intmat expo_vecs=mons2intmat(I);
1256
1257    string dummy=collectNmzOptions(); // only to set GenGen
1258    return( intmat2mons( runNormaliz(expo_vecs,nmz_mode, prepareGrading(#)) ) );
1259}
1260
1261proc intclToricRing(ideal I, list #)
1262"USAGE:   intclToricRing(ideal I);
1263          intclToricRing(ideal I, intvec grading);
1264RETURN:   The toric ring S is the subalgebra of the basering generated by
1265          the leading monomials of the elements of I (considered as a list
1266          of polynomials). The function computes the integral
1267          closure T of S in the basering and returns an ideal listing
1268          the algebra generators of T over the coefficient field.
1269@*        The function returns the input ideal I if one of the options
1270          @code{supp}, @code{triang}, @code{volume}, or @code{hseries}
1271          has been activated.
1272          However, in this case some numerical invariants are computed, and
1273          some other data may be contained in files that you can read into
1274          Singular (see @ref{showNuminvs}, @ref{exportNuminvs}).
1275NOTE:     A mathematical remark: the toric ring depends on the list of
1276          monomials given, and not only on the ideal they generate!
1277SEE ALSO:  normalToricRing, ehrhartRing, intclMonIdeal
1278EXAMPLE:   example intclToricRing; shows an example
1279"
1280{
1281    return(runIntclToricRing(I,0,#));
1282}
1283example
1284{ "EXAMPLE:"; echo=2;
1285  ring R=37,(x,y,t),dp;
1286  ideal I=x3,x2y,y3;
1287  intclToricRing(I);
1288  showNuminvs();
1289  //now the same example with another grading
1290  intvec grading = 2,3,1;
1291  intclToricRing(I,grading);
1292  showNuminvs();
1293
1294}
1295
1296proc normalToricRing(ideal I, list #)
1297"USAGE:   normalToricRing(ideal I);
1298          normalToricRing(ideal I, intvec grading);
1299RETURN:   The toric ring S is the subalgebra of the basering generated by the
1300          leading monomials of the elements of I (considered as a list of
1301          polynomials). The function computes the
1302          normalisation T of S and returns an ideal listing the algebra
1303          generators of T over the coefficient field.
1304@*        The function returns the input ideal I if one of the options
1305          @code{supp}, @code{triang}, @code{volume}, or @code{hseries}
1306          has been activated.
1307          However, in this case some numerical invariants are computed, and
1308          some other data may be contained in files that you can read into
1309          Singular (see @ref{showNuminvs}, @ref{exportNuminvs}).
1310NOTE:     A mathematical remark: the toric ring depends on the list of
1311          monomials given, and not only on the ideal they generate!
1312SEE ALSO: intclToricRing, ehrhartRing, intclMonIdeal, normalToricRingFromBinomials
1313EXAMPLE:  example normalToricRing; shows an example
1314"
1315{
1316    return(runIntclToricRing(I,1,#));
1317}
1318example
1319{ "EXAMPLE:"; echo=2;
1320  ring  R = 37,(x,y,t),dp;
1321  ideal I = x3,x2y,y3;
1322  normalToricRing(I);
1323}
1324
1325
1326proc normalToricRingFromBinomials(ideal I, list #)
1327"USAGE:   normalToricRingFromBinomials(ideal I);
1328          normalToricRingFromBinomials(ideal I, intvec grading);
1329RETURN:   @texinfo
1330@tex
1331The ideal $I$ is generated by binomials of type $X^a-X^b$ (multiindex notation)
1332in the surrounding polynomial ring $K[X]=K[X_1,...,X_n]$. The binomials
1333represent a congruence on the monoid ${Z}^n$ with residue monoid $M$.
1334Let $N$ be the image of $M$ in gp($M$)/torsion. Then $N$ is universal in the
1335sense that every homomorphism from $M$ to an affine monoid factors through $N$.
1336If $I$ is a prime ideal, then $K[N]= K[X]/I$. In general, $K[N]=K[X]/P$ where
1337$P$ is the unique minimal prime ideal of $I$ generated by binomials of type
1338$X^a-X^b$.
1339
1340The function computes the normalization of $K[N]$ and returns a newly created
1341polynomial ring of the same Krull dimension, whose variables are
1342$x(1),...,x(n-r)$, where $r$ is the rank of the matrix with rows $a-b$.
1343(In general there is no canonical choice for such an embedding.)
1344Inside this polynomial ring there is an ideal $I$ which lists the algebra
1345generators of the normalization of $K[N]$.
1346@end tex
1347@end texinfo
1348@*        The function returns the input ideal I if one of the options
1349          @code{supp}, @code{triang}, @code{volume}, or @code{hseries}
1350          has been activated.
1351          However, in this case some numerical invariants are computed, and
1352          some other data may be contained in files that you can read into
1353          Singular (see @ref{showNuminvs}, @ref{exportNuminvs}).
1354SEE ALSO: intclToricRing, normalToricRing, ehrhartRing, intclMonIdeal
1355EXAMPLE:  example normalToricRing; shows an example
1356"
1357{
1358    intmat expo_vecs = binomials2intmat(I);
1359    string dummy=collectNmzOptions(); // only to set GenGen
1360    intmat result = runNormaliz(expo_vecs,10,prepareGrading(#));
1361
1362    list baseringlist = ringlist(basering);
1363    ring S = (baseringlist[1]),(x(1..ncols(result))),dp;
1364    ideal I = intmat2mons(result);
1365    export(I);
1366    return (S);
1367}
1368example
1369{ "EXAMPLE:"; echo=2;
1370  ring R = 37,(u,v,w,x,y,z),dp;
1371  ideal I = u2v-xyz, ux2-wyz, uvw-y2z;
1372  def S = normalToricRingFromBinomials(I);
1373  setring S;
1374  I;
1375}
1376
1377static proc runIntclMonIdeal(ideal I, int nmz_mode, list #)
1378{
1379    intmat expo_vecs=mons2intmat(I);
1380    int i,last_comp;
1381
1382    // we test if there is room for the Rees algebra
1383
1384    for(i=1;i<=nrows(expo_vecs);i++)
1385    {
1386        if(expo_vecs[i,ncols(expo_vecs)]!=0)
1387        {
1388            last_comp=1;  break; // no
1389        }
1390    }
1391
1392    string dummy=collectNmzOptions(); // only to set GenGen
1393
1394    //adjust size of input matrix
1395    if (!last_comp) { // remove last component
1396        intmat tmp[nrows(expo_vecs)][ncols(expo_vecs)-1]
1397               = expo_vecs[1..nrows(expo_vecs),1..(ncols(expo_vecs)-1)];
1398        expo_vecs = tmp;
1399    }
1400    intmat nmz_data=runNormaliz(expo_vecs,nmz_mode,prepareGrading(#));
1401
1402    if(last_comp)
1403    {
1404        ideal I1=intmat2monsSel(nmz_data,1);
1405        return(list(I1));
1406    }
1407    else
1408    {
1409        ideal I1=intmat2monsSel(nmz_data,1);
1410        ideal I2=intmat2mons(nmz_data);
1411        return(list(I1,I2));
1412    }
1413}
1414
1415proc ehrhartRing(ideal I)
1416"USAGE:    ehrhartRing(ideal I);
1417RETURN:    The exponent vectors of the leading monomials of the elements of I
1418           are considered as points of a lattice polytope P.
1419           The Ehrhart ring of a (lattice) polytope P is the monoid algebra
1420           defined by the monoid of lattice points in the cone over the
1421           polytope P; see Bruns and Gubeladze, Polytopes, Rings, and K-theory,
1422           Springer 2009, pp. 228, 229.
1423           The function returns a list of ideals:
1424@*         (i) If the last ring variable is not used by the monomials, it is
1425               treated as the auxiliary variable of the Ehrhart ring. The
1426               function returns two ideals, the first containing the monomials
1427               representing all the lattice points of the polytope, the second
1428               containing the algebra generators of the Ehrhart ring over the
1429               coefficient field.
1430@*         (ii) If the last ring variable is used by the monomials, the list
1431                returned contains only one ideal, namely the monomials
1432                representing the lattice points of the polytope.
1433@*
1434@*        The function returns the a list containing the input ideal I if one
1435          of the options @code{supp}, @code{triang}, @code{volume}, or
1436          @code{hseries} has been activated.
1437          However, in this case some numerical invariants are computed, and
1438          some other data may be contained in files that you can read into
1439          Singular (see @ref{showNuminvs}, @ref{exportNuminvs}).
1440NOTE:      A mathematical remark: the Ehrhart ring depends on the list of
1441           monomials given, and not only on the ideal they generate!
1442SEE ALSO: intclToricRing, normalToricRing, intclMonIdeal
1443EXAMPLE:  example ehrhartRing; shows an example
1444"
1445{
1446    return(runIntclMonIdeal(I,2));
1447}
1448example
1449{ "EXAMPLE:"; echo=2;
1450  ring R=37,(x,y,t),dp;
1451  ideal J=x3,x2y,y3,xy2t7;
1452  ehrhartRing(J);
1453}
1454
1455proc intclMonIdeal(ideal I, list #)
1456"USAGE:   intclMonIdeal(ideal I);
1457          intclMonIdeal(ideal I, intvec grading);
1458RETURN:   The exponent vectors of the leading monomials of the elements of I
1459          are considered as generators of a monomial ideal for which the
1460          normalization of its Rees algebra is computed. For a Definiton of the
1461          Rees algebra (or Rees ring) see Bruns and Herzog, Cohen-Macaulay
1462          rings, Cambridge University Press 1998, p. 182.
1463          The function returns a list of ideals:
1464@* (i) If the last ring variable is not used by the monomials, it is treated
1465       as the auxiliary variable of the Rees algebra. The function returns two
1466       ideals, the first containing the monomials generating the integral
1467       closure of the monomial ideal, the second containing the algebra
1468         generators of the normalization of the Rees algebra.
1469@* (ii) If the last ring variable is used by the monomials, the list returned
1470        contains only one ideal, namely the monomials generating the integral
1471        closure of the ideal.
1472@*        The function returns the a list containing the input ideal I if one
1473          of the options @code{supp}, @code{triang}, @code{volume}, or
1474          @code{hseries} has been activated.
1475          However, in this case some numerical invariants are computed, and
1476          some other data may be contained in files that you can read into
1477          Singular (see @ref{showNuminvs}, @ref{exportNuminvs}).
1478SEE ALSO: intclToricRing, normalToricRing, ehrhartRing
1479EXAMPLE:  example intclMonIdeal; shows an example
1480"
1481{
1482    return(runIntclMonIdeal(I,3,#));
1483}
1484example
1485{ "EXAMPLE"; echo=2;
1486    ring R=0,(x,y,z,t),dp;
1487    ideal I=x^2,y^2,z^3;
1488    list l=intclMonIdeal(I);
1489    l[1]; // integral closure of I
1490    l[2];  // monomials generating the integral closure of the Rees algebra
1491}
1492
1493// torus invariants and valuation rings and ideals
1494
1495proc torusInvariants(intmat E, list #)
1496"USAGE:   torusInvariants(intmat A);
1497          torusInvariants(intmat A, intvec grading);
1498RETURN:   @texinfo
1499Returns an ideal representing the list of monomials generating the ring of
1500invariants as an algebra over the coefficient field.
1501@tex
1502$R^T$.
1503@end tex
1504@*        The function returns the ideal given by the input matrix A if one of
1505          the options @code{supp}, @code{triang}, @code{volume}, or
1506          @code{hseries} has been activated.
1507          However, in this case some numerical invariants are computed, and
1508          some other data may be contained in files that you can read into
1509          Singular (see @ref{showNuminvs}, @ref{exportNuminvs}).
1510@end texinfo
1511BACKGROUND: @texinfo
1512@tex
1513 Let $T = (K^*)^r$ be the $r$-dimensional torus acting on the polynomial ring
1514 $R = K[X_1 ,\ldots,X_n]$ diagonally. Such an action can be described as
1515 follows: there are integers $a_{i,j}$, $i=1,\ldots,r$, $j=1,\ldots,n$, such
1516 that $(\lambda_1,\ldots,\lambda_r)\in T$ acts by the substitution
1517$$ X_j \mapsto \lambda_1^{a_{1,j}} \cdots \lambda_r^{a_{r,j}}X_j,
1518   \quad j=1,\ldots,n.$$
1519In order to compute the ring of invariants $R^T$ one must specify the matrix
1520$A=(a_{i,j})$.
1521@end tex
1522@end texinfo
1523SEE ALSO: diagInvariants, finiteDiagInvariants, intersectionValRings,
1524          intersectionValRingIdeals
1525EXAMPLE:  example torusInvariants; shows an example
1526"
1527{
1528    if(nvars(basering)!=ncols(E))
1529    {
1530        ERROR("torusInvariants: wrong number of columns in matrix");
1531    }
1532
1533    string dummy=collectNmzOptions();  // only to set GenGen
1534
1535    return( intmat2mons( runNormaliz(E,5,prepareGrading(#)) ) );
1536}
1537example
1538{ "EXAMPLE:"; echo=2;
1539  ring R=0,(x,y,z,w),dp;
1540  intmat E[2][4] = -1,-1,2,0, 1,1,-2,-1;
1541  torusInvariants(E);
1542}
1543
1544proc finiteDiagInvariants(intmat C, list #)
1545"USAGE:   finiteDiagInvariants(intmat U);
1546          finiteDiagInvariants(intmat U, intvec grading);
1547RETURN:   @texinfo
1548@tex
1549This function computes the ring of invariants of a finite abelian group $G$
1550acting diagonally on the surrounding polynomial ring $K[X_1,...,X_n]$. The
1551group is the direct product of cyclic groups generated by finitely many
1552elements $g_1,...,g_w$. The element $g_i$ acts on the indeterminate $X_j$ by
1553$g_i(X_j)=\lambda_i^{u_{ij}}X_j$ where $\lambda_i$ is a primitive root of
1554unity of order equal to $ord(g_i)$. The ring of invariants is generated by all
1555monomials satisfying the system
1556$u_{i1}a_1+\ldots+u_{in} a_n \equiv 0$ mod ord$(g_i)$, $i=1,\ldots,w$.
1557The input to the function is the $w\times(n+1)$ matrix $U$ with rows
1558$u_{i1}\ldots u_{in}$ ord$(gi)$, $i=1,\ldots,w$. The output is a monomial ideal
1559listing the algebra generators of the subalgebra of invariants
1560{$R^G=\{f\in R : g_i f = f$ for all $i=1,\ldots,w\}$}.
1561@end tex
1562@end texinfo
1563@*        The function returns the ideal given by the input matrix C if one of
1564          the options @code{supp}, @code{triang}, @code{volume}, or
1565          @code{hseries} has been activated.
1566          However, in this case some numerical invariants are computed, and
1567          some other data may be contained in files that you can read into
1568          Singular (see @ref{showNuminvs}, @ref{exportNuminvs}).
1569NOTE:
1570SEE ALSO: torusInvariants, diagInvariants, intersectionValRings,
1571          intersectionValRingIdeals
1572EXAMPLE:  example finiteDiagInvariants; shows an example
1573"
1574{
1575    if(nvars(basering)!=ncols(C)-1)
1576    {
1577        ERROR("finiteDiagInvariants: wrong number of columns in matrix");
1578    }
1579
1580    string dummy=collectNmzOptions();  // only to set GenGen
1581
1582    return( intmat2mons( runNormaliz(C,6,prepareGrading(#)) ) );
1583}
1584example
1585{ "EXAMPLE:"; echo=2;
1586  ring R = 0,(x,y,z,w),dp;
1587  intmat C[2][5] = 1,1,1,1,5, 1,0,2,0,7;
1588  finiteDiagInvariants(C);
1589}
1590
1591proc diagInvariants(intmat E, intmat C, list #)
1592"USAGE:   diagInvariants(intmat A, intmat U);
1593          diagInvariants(intmat A, intmat U, intvec grading);
1594RETURN:   @texinfo
1595@tex
1596This function computes the ring of invariants of a diagonalizable group
1597$D = T\times G$ where $T$ is a torus and $G$ is a finite abelian group, both
1598acting diagonally on the polynomial ring $K[X_1,\ldots,X_n]$. The group
1599actions are specified by the input matrices A and U. The first matrix specifies
1600the torus action, the second the action of the finite group. See
1601torusInvariants and finiteDiagInvariants for more detail. The output is a
1602monomial ideal listing the algebra generators of the subalgebra of invariants.
1603@end tex
1604@end texinfo
1605@*        The function returns the ideal given by the input matrix A if one of
1606          the options @code{supp}, @code{triang}, @code{volume}, or
1607          @code{hseries} has been activated.
1608          However, in this case some numerical invariants are computed, and
1609          some other data may be contained in files that you can read into
1610          Singular (see @ref{showNuminvs}, @ref{exportNuminvs}).
1611SEE ALSO: torusInvariants, finiteDiagInvariants, intersectionValRings, intersectionValRingIdeals
1612EXAMPLE:  example diagInvariants; shows an example
1613"
1614{
1615    if(nvars(basering)!=ncols(E) || nvars(basering)!=ncols(C)-1)
1616    {
1617        ERROR("diagInvariants: wrong number of columns in matrix");
1618    }
1619
1620    string dummy=collectNmzOptions();  // only to set GenGen
1621
1622    return( intmat2mons( runNormaliz(E,5,C,6,prepareGrading(#)) ) );
1623}
1624example
1625{ "EXAMPLE:"; echo=2;
1626  ring R=0,(x,y,z,w),dp;
1627  intmat E[2][4] = -1,-1,2,0, 1,1,-2,-1;
1628  intmat C[2][5] = 1,1,1,1,5, 1,0,2,0,7;
1629  diagInvariants(E,C);
1630}
1631
1632proc intersectionValRings(intmat V, list #)
1633"USAGE:   intersectionValRings(intmat V, intvec grading);
1634RETURN:   The function returns a monomial ideal, to be considered as the list
1635          of monomials generating @math{S} as an algebra over the coefficient
1636          field.
1637BACKGROUND: @texinfo
1638@tex
1639A discrete monomial valuation $v$ on $R = K[X_1 ,\ldots,X_n]$ is determined by
1640the values $v(X_j)$ of the indeterminates. This function computes the
1641subalgebra $S = \{ f \in R : v_i ( f ) \geq 0,\ i = 1,\ldots,r\}$ for several
1642such valuations $v_i$, $i=1,\ldots,r$. It needs the matrix $V = (v_i(X_j))$ as
1643its input.
1644@end tex
1645@end texinfo
1646@*        The function returns the ideal given by the input matrix V if one of
1647          the options @code{supp}, @code{triang}, @code{volume}, or
1648          @code{hseries} has been activated.
1649          However, in this case some numerical invariants are computed, and
1650          some other data may be contained in files that you can read into
1651          Singular (see @ref{showNuminvs}, @ref{exportNuminvs}).
1652SEE ALSO: torusInvariants, diagInvariants, finiteDiagInvariants, intersectionValRingIdeals
1653EXAMPLE:  example intersectionValRings; shows an example
1654"
1655{
1656
1657    if(nvars(basering)!=ncols(V))
1658    {
1659        ERROR("intersectionValRings: wrong number of columns in matrix");
1660    }
1661
1662    intmat V1[nrows(V)+ncols(V)][ncols(V)];
1663    int i,j;
1664
1665    for(i=1;i<=ncols(V);i++)
1666    {
1667        V1[i,i]=1;
1668    }
1669    for(i=1;i<=nrows(V);i++)
1670    {
1671        for(j=1;j<=ncols(V);j++)
1672        {
1673            V1[i+ncols(V),j]=V[i,j];
1674        }
1675    }
1676
1677
1678    string dummy=collectNmzOptions();  // only to set GenGen
1679
1680/*    if(!GenGen) // return V
1681    {
1682        runNormaliz(V1,4,prepareGrading(#));
1683        return(V);
1684    }
1685*/
1686    return(intmat2mons(runNormaliz(V1,4,prepareGrading(#))));
1687}
1688example
1689{ "EXAMPLE:"; echo=2;
1690  ring R=0,(x,y,z,w),dp;
1691  intmat V0[2][4]=0,1,2,3, -1,1,2,1;
1692  intersectionValRings(V0);
1693}
1694
1695proc intersectionValRingIdeals(intmat V, list #)
1696"USAGE:   intersectionValRingIdeals(intmat V);
1697          intersectionValRingIdeals(intmat V, intvec grading);
1698RETURN:   The function returns two ideals, both to be considered as lists of
1699          monomials. The
1700          first is the system of monomial generators of @math{S}, the second
1701          the system of generators of @math{M}.
1702@*        The function returns a list consisting of the ideal given by the
1703          input matrix T if one of the options @code{supp}, @code{triang}, or
1704          @code{hvect} has been activated.
1705          However, in this case some numerical invariants are computed, and
1706          some other data may be contained in files that you can read into
1707          Singular (see @ref{showNuminvs}, @ref{exportNuminvs}).
1708BACKGROUND: @texinfo
1709@tex
1710A discrete monomial valuation $v$ on $R = K[X_1 ,\ldots,X_n]$ is determined by
1711the values $v(X_j)$ of the indeterminates. This function computes the
1712subalgebra $S = \{ f \in R : v_i ( f ) \geq 0,\ i = 1,\ldots,r\}$ for several
1713such valuations $v_i$, $i=1,\ldots,r$. It needs the matrix $V = (v_i(X_j))$ as
1714its input.
1715
1716This function simultaneously determines the $S$-submodule
1717$M = \{ f \in R : v_i(f) \geq w_i ,\ i = 1,\ldots,r\}$ for integers
1718$w_1,\ldots\,w_r$. (If $w_i \geq 0$ for all $i$, $M$ is an ideal of $S$.)
1719The numbers $w_i$ form the $(n+1)$th column of the input matrix.
1720@end tex
1721@end texinfo
1722NOTE:   The function also gives an error message if the matrix V has the
1723        wrong number of columns.
1724SEE ALSO: torusInvariants, diagInvariants, finiteDiagInvariants, intersectionValRings
1725EXAMPLE:  example intersectionValRingIdeals; shows an example
1726"
1727{
1728    if(nvars(basering)!=ncols(V)-1)
1729    {
1730        ERROR("intersectionValRingIdeals: wrong number of columns in matrix");
1731    }
1732
1733    intmat V1[nrows(V)+ncols(V)][ncols(V)];
1734    int i,j;
1735
1736    for(i=1;i<=ncols(V);i++)
1737    {
1738        V1[i,i]=1;
1739    }
1740    for(i=1;i<=nrows(V);i++)
1741    {
1742        for(j=1;j<=ncols(V);j++)
1743        {
1744            V1[i+ncols(V),j]=V[i,j];
1745        }
1746    }
1747    for(i=1;i<=nrows(V);i++)
1748    {
1749        V1[i+ncols(V),ncols(V)]=-V1[i+ncols(V),ncols(V)];
1750    }
1751
1752    string dummy=collectNmzOptions();  // only to set GenGen
1753
1754    intmat nmz_data=runNormaliz(V1,4,prepareGrading(#));
1755
1756    ideal I1=intmat2monsSel(nmz_data,0);
1757    ideal I2=intmat2monsSel(nmz_data,1);
1758    return(list(I1,I2));
1759}
1760example
1761{ "EXAMPLE:"; echo=2;
1762 ring R=0,(x,y,z,w),dp;
1763 intmat V[2][5]=0,1,2,3,4, -1,1,2,1,3;
1764 intersectionValRingIdeals(V);
1765}
Note: See TracBrowser for help on using the repository browser.