--* From bmt@spadserv.watson.ibm.com  Thu Jan 21 08:44:43 1993
--* Received: from spadserv.watson.ibm.com by radical.watson.ibm.com (AIX 3.2/UCB 5.64/900524)
--*           id AA13062; Thu, 21 Jan 1993 08:44:43 -0500
--* Received: by spadserv.watson.ibm.com (AIX 3.2/UCB 5.64/900524)
--*           id AA30813; Thu, 21 Jan 1993 08:51:37 -0500
--* Date: Thu, 21 Jan 1993 08:51:37 -0500
--* From: bmt@spadserv.watson.ibm.com
--* X-External-Networks: yes
--* Message-Id: <9301211351.AA30813@spadserv.watson.ibm.com>
--* To: axc-bug@radical.watson.ibm.com
--* Subject: Bug: Bad foam reference in const 0: 25.3

--@ Fixed  by: JMS Wed Oct 13 10:01:33 1993
--@ Tested by: <name of new or existing file in test directory>
--@ Summary:   <One line description of real problem and the fix>


#include "aslib.as"

-- This file computes hilbert functions for monomial ideals
-- ref: "On the Computation of Hilbert-Poincare Series", Bigatti, Caboara, Robbiano,
-- AAECC vol 2 #1 (1991) pp 21-33 

--#library arraylib "array.aso"
--#library listlib "list.aso"
--import arraylib
--import listlib

macro 
  Monom == Array(SingleInteger)
  L == List
  SI == SingleInteger
  empty() == nil
  xx <= yy == not(xx > yy)
  xx > yy == yy < xx
  B == Boolean

import Monom
import SingleInteger

divides?(m1:Monom, m2:Monom):B ==
  for e1 in m1 for e2 in m2 repeat
    if e1 > e2 then return false
  true

(m1:Monom) < (m2:Monom):B ==
  for e1 in m1 for e2 in m2 repeat
    if e1 < e2 then return true
    if e1 > e2 then return false
  false

adjoin(m:Monom, lm:L Monom):L Monom ==
  empty?(lm) => cons(m, nil)
  ris1:= empty()
  ris2:= empty()
  local m1 : Monom
  while not empty? lm repeat
    m1 := first lm
    lm := rest lm
    m <= m1 =>
       not divides?(m,m1) => ris1 := cons(m1, ris1)
    if divides?(m1, m) then
       return concat!(reverse!(ris1), concat!(reverse! ris2, lm))
    ris2 := cons(m1, ris2)
  concat!(reverse!(ris1), cons(m1, reverse! ris2))

reduce(lm:L Monom):L Monom ==
  ris := empty()
  for m in lm repeat
    ris := adjoin(m, ris)
  ris

merge(l1:L Monom, l2:L Monom):L Monom ==
  #l1 > #l2 => merge(l2,l1)
  ris := l2
  for m1 in l1 repeat ris := adjoin(m1, ris)
  ris

-- decompose(I:L Monom, v:SI):L Record(deg:SI, ideal:L Monom) ==
  
--m:Monom := array(1 for i in 1..3)
 
