0001: /*
0002: * xtc - The eXTensible Compiler
0003: * Copyright (C) 2007 Robert Grimm, New York University
0004: *
0005: * This library is free software; you can redistribute it and/or
0006: * modify it under the terms of the GNU Lesser General Public License
0007: * version 2.1 as published by the Free Software Foundation.
0008: *
0009: * This library is distributed in the hope that it will be useful,
0010: * but WITHOUT ANY WARRANTY; without even the implied warranty of
0011: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
0012: * Lesser General Public License for more details.
0013: *
0014: * You should have received a copy of the GNU Lesser General Public
0015: * License along with this library; if not, write to the Free Software
0016: * Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
0017: * USA.
0018: */
0019: package xtc.typical;
0020:
0021: import java.math.BigInteger;
0022: import java.util.Hashtable;
0023: import java.util.HashSet;
0024: import java.util.Set;
0025: import java.util.HashMap;
0026: import java.util.Iterator;
0027:
0028: import xtc.tree.Node;
0029:
0030: import xtc.util.Pair;
0031: import xtc.util.Function;
0032:
0033: /**
0034: * The primitives for Typical.
0035: *
0036: * @author Robert Grimm
0037: * @version $Revision: 1.48 $
0038: */
0039: public class Primitives {
0040:
0041: /** The minimum integer value as a big integer. */
0042: private static final BigInteger INT_MIN = BigInteger
0043: .valueOf(Integer.MIN_VALUE);
0044:
0045: /** The maximum integer value as a big integer. */
0046: private static final BigInteger INT_MAX = BigInteger
0047: .valueOf(Integer.MAX_VALUE);
0048:
0049: private Primitives() { /* Nothing to do. */
0050: }
0051:
0052: // =========================================================================
0053: // Helper methods
0054: // =========================================================================
0055:
0056: /**
0057: * Convert the specified big integer to an int value.
0058: *
0059: * @param val The big integer.
0060: * @return The corresponding int value.
0061: * @throws IllegalArgumentException Signals that the big integer's
0062: * value is too large.
0063: */
0064: public static final int toInt(BigInteger val) {
0065: if ((val.compareTo(INT_MIN) < 0)
0066: || (val.compareTo(INT_MAX) > 0)) {
0067: throw new IllegalArgumentException("integer too large: "
0068: + val);
0069: }
0070: return val.intValue();
0071: }
0072:
0073: /**
0074: * Trace the specified object.
0075: *
0076: * @param msg The message prefix.
0077: * @param o The object.
0078: */
0079: public static final void trace(String msg, Object o) {
0080: System.out.print(msg);
0081: if (null == o) {
0082: System.out.println("bottom");
0083: } else {
0084: System.out.println(o.toString());
0085: }
0086: System.out.flush();
0087: }
0088:
0089: // =========================================================================
0090: // Testing for bottom
0091: // =========================================================================
0092:
0093: /** Test a value for bottom. */
0094: public static final Function.F1<Boolean, Object> isBottom = new Function.F1<Boolean, Object>() {
0095: public Boolean apply(Object o) {
0096: return null == o;
0097: }
0098: };
0099:
0100: // -------------------------------------------------------------------------
0101:
0102: /** Test a value for not being bottom. */
0103: public static final Function.F1<Boolean, Object> isNotBottom = new Function.F1<Boolean, Object>() {
0104: public Boolean apply(Object o) {
0105: return null != o;
0106: }
0107: };
0108:
0109: // =========================================================================
0110: // Boolean operations
0111: // =========================================================================
0112:
0113: /** Negate a boolean. */
0114: public static final Function.F1<Boolean, Boolean> not = new Function.F1<Boolean, Boolean>() {
0115: public Boolean apply(Boolean val) {
0116: return null == val ? null : !val;
0117: }
0118: };
0119:
0120: // -------------------------------------------------------------------------
0121:
0122: /** And two booleans. */
0123: public static final Function.F2<Boolean, Boolean, Boolean> and = new Function.F2<Boolean, Boolean, Boolean>() {
0124: public Boolean apply(Boolean val1, Boolean val2) {
0125: return (null == val1) || (null == val2) ? null : val1
0126: && val2;
0127: }
0128: };
0129:
0130: // -------------------------------------------------------------------------
0131:
0132: /** Or two booleans. */
0133: public static final Function.F2<Boolean, Boolean, Boolean> or = new Function.F2<Boolean, Boolean, Boolean>() {
0134: public Boolean apply(Boolean val1, Boolean val2) {
0135: return (null == val1) || (null == val2) ? null : val1
0136: || val2;
0137: }
0138: };
0139:
0140: // =========================================================================
0141: // Comparsion operations
0142: // =========================================================================
0143:
0144: /** Determine whether two objects are equal. */
0145: public static final Function.F2<Boolean, Object, Object> equal = new Function.F2<Boolean, Object, Object>() {
0146: public Boolean apply(Object val1, Object val2) {
0147: return (null == val1) || (null == val2) ? null : val1
0148: .equals(val2);
0149: }
0150: };
0151:
0152: // -------------------------------------------------------------------------
0153:
0154: /** Determine whether one big integer is less than another. */
0155: public static final Function.F2<Boolean, BigInteger, BigInteger> lessInt = new Function.F2<Boolean, BigInteger, BigInteger>() {
0156: public Boolean apply(BigInteger val1, BigInteger val2) {
0157: return (null == val1) || (null == val2) ? null : val1
0158: .compareTo(val2) < 0;
0159: }
0160: };
0161:
0162: // -------------------------------------------------------------------------
0163:
0164: /** Determine whether one double is less than another. */
0165: public static final Function.F2<Boolean, Double, Double> lessFloat64 = new Function.F2<Boolean, Double, Double>() {
0166: public Boolean apply(Double val1, Double val2) {
0167: return (null == val1) || (null == val2) ? null
0168: : val1 < val2;
0169: }
0170: };
0171:
0172: // -------------------------------------------------------------------------
0173:
0174: /** Determine whether one float is less than another. */
0175: public static final Function.F2<Boolean, Float, Float> lessFloat32 = new Function.F2<Boolean, Float, Float>() {
0176: public Boolean apply(Float val1, Float val2) {
0177: return (null == val1) || (null == val2) ? null
0178: : val1 < val2;
0179: }
0180: };
0181:
0182: // -------------------------------------------------------------------------
0183:
0184: /** Determine whether one big integer is less equal than another. */
0185: public static final Function.F2<Boolean, BigInteger, BigInteger> lessEqualInt = new Function.F2<Boolean, BigInteger, BigInteger>() {
0186: public Boolean apply(BigInteger val1, BigInteger val2) {
0187: return (null == val1) || (null == val2) ? null : val1
0188: .compareTo(val2) <= 0;
0189: }
0190: };
0191:
0192: // -------------------------------------------------------------------------
0193:
0194: /** Determine whether one double is greater than another. */
0195: public static final Function.F2<Boolean, Double, Double> lessEqualFloat64 = new Function.F2<Boolean, Double, Double>() {
0196: public Boolean apply(Double val1, Double val2) {
0197: return (null == val1) || (null == val2) ? null
0198: : val1 <= val2;
0199: }
0200: };
0201:
0202: // -------------------------------------------------------------------------
0203:
0204: /** Determine whether one float is greater than another. */
0205: public static final Function.F2<Boolean, Float, Float> lessEqualFloat32 = new Function.F2<Boolean, Float, Float>() {
0206: public Boolean apply(Float val1, Float val2) {
0207: return (null == val1) || (null == val2) ? null
0208: : val1 <= val2;
0209: }
0210: };
0211:
0212: // -------------------------------------------------------------------------
0213:
0214: /** Determine whether one big integer is greater than another. */
0215: public static final Function.F2<Boolean, BigInteger, BigInteger> greaterInt = new Function.F2<Boolean, BigInteger, BigInteger>() {
0216: public Boolean apply(BigInteger val1, BigInteger val2) {
0217: return (null == val1) || (null == val2) ? null : val1
0218: .compareTo(val2) > 0;
0219: }
0220: };
0221:
0222: // -------------------------------------------------------------------------
0223:
0224: /** Determine whether one double is greater than another. */
0225: public static final Function.F2<Boolean, Double, Double> greaterFloat64 = new Function.F2<Boolean, Double, Double>() {
0226: public Boolean apply(Double val1, Double val2) {
0227: return (null == val1) || (null == val2) ? null
0228: : val1 > val2;
0229: }
0230: };
0231:
0232: // -------------------------------------------------------------------------
0233:
0234: /** Determine whether one float is greater than another. */
0235: public static final Function.F2<Boolean, Float, Float> greaterFloat32 = new Function.F2<Boolean, Float, Float>() {
0236: public Boolean apply(Float val1, Float val2) {
0237: return (null == val1) || (null == val2) ? null
0238: : val1 > val2;
0239: }
0240: };
0241:
0242: // -------------------------------------------------------------------------
0243:
0244: /** Determine whether one big integer is greater equal than another. */
0245: public static final Function.F2<Boolean, BigInteger, BigInteger> greaterEqualInt = new Function.F2<Boolean, BigInteger, BigInteger>() {
0246: public Boolean apply(BigInteger val1, BigInteger val2) {
0247: return (null == val1) || (null == val2) ? null : val1
0248: .compareTo(val2) >= 0;
0249: }
0250: };
0251:
0252: // -------------------------------------------------------------------------
0253:
0254: /** Determine whether one double is greater than another. */
0255: public static final Function.F2<Boolean, Double, Double> greaterEqualFloat64 = new Function.F2<Boolean, Double, Double>() {
0256: public Boolean apply(Double val1, Double val2) {
0257: return (null == val1) || (null == val2) ? null
0258: : val1 >= val2;
0259: }
0260: };
0261:
0262: // -------------------------------------------------------------------------
0263:
0264: /** Determine whether one float is greater than another. */
0265: public static final Function.F2<Boolean, Float, Float> greaterEqualFloat32 = new Function.F2<Boolean, Float, Float>() {
0266: public Boolean apply(Float val1, Float val2) {
0267: return (null == val1) || (null == val2) ? null
0268: : val1 >= val2;
0269: }
0270: };
0271:
0272: // =========================================================================
0273: // Arithmetic operations
0274: // =========================================================================
0275:
0276: /** Negate a big integer. */
0277: public static final Function.F1<BigInteger, BigInteger> negateInt = new Function.F1<BigInteger, BigInteger>() {
0278: public BigInteger apply(BigInteger val) {
0279: return null == val ? null : val.negate();
0280: }
0281: };
0282:
0283: // -------------------------------------------------------------------------
0284:
0285: /** Negate a double. */
0286: public static final Function.F1<Double, Double> negateFloat64 = new Function.F1<Double, Double>() {
0287: public Double apply(Double val) {
0288: return null == val ? null : -val;
0289: }
0290: };
0291:
0292: // -------------------------------------------------------------------------
0293:
0294: /** Negate a float. */
0295: public static final Function.F1<Float, Float> negateFloat32 = new Function.F1<Float, Float>() {
0296: public Float apply(Float val) {
0297: return null == val ? null : -val;
0298: }
0299: };
0300:
0301: // -------------------------------------------------------------------------
0302:
0303: /** Affirm a big integer. */
0304: public static final Function.F1<BigInteger, BigInteger> absInt = new Function.F1<BigInteger, BigInteger>() {
0305: public BigInteger apply(BigInteger val) {
0306: return null == val ? null : val.abs();
0307: }
0308: };
0309:
0310: // -------------------------------------------------------------------------
0311:
0312: /** Affirm a double. */
0313: public static final Function.F1<Double, Double> absFloat64 = new Function.F1<Double, Double>() {
0314: public Double apply(Double val) {
0315: return null == val ? null : +val;
0316: }
0317: };
0318:
0319: // -------------------------------------------------------------------------
0320:
0321: /** Affirm a float. */
0322: public static final Function.F1<Float, Float> absFloat32 = new Function.F1<Float, Float>() {
0323: public Float apply(Float val) {
0324: return null == val ? null : +val;
0325: }
0326: };
0327:
0328: // -------------------------------------------------------------------------
0329:
0330: /** Add two big integers. */
0331: public static final Function.F2<BigInteger, BigInteger, BigInteger> addInt = new Function.F2<BigInteger, BigInteger, BigInteger>() {
0332: public BigInteger apply(BigInteger val1, BigInteger val2) {
0333: return (null == val1) || (null == val2) ? null : val1
0334: .add(val2);
0335: }
0336: };
0337:
0338: // -------------------------------------------------------------------------
0339:
0340: /** Add two doubles. */
0341: public static final Function.F2<Double, Double, Double> addFloat64 = new Function.F2<Double, Double, Double>() {
0342: public Double apply(Double val1, Double val2) {
0343: return (null == val1) || (null == val2) ? null : val1
0344: + val2;
0345: }
0346: };
0347:
0348: // -------------------------------------------------------------------------
0349:
0350: /** Add two floats. */
0351: public static final Function.F2<Float, Float, Float> addFloat32 = new Function.F2<Float, Float, Float>() {
0352: public Float apply(Float val1, Float val2) {
0353: return (null == val1) || (null == val2) ? null : val1
0354: + val2;
0355: }
0356: };
0357:
0358: // -------------------------------------------------------------------------
0359:
0360: /** Subtract two big integers. */
0361: public static final Function.F2<BigInteger, BigInteger, BigInteger> subtractInt = new Function.F2<BigInteger, BigInteger, BigInteger>() {
0362: public BigInteger apply(BigInteger val1, BigInteger val2) {
0363: return (null == val1) || (null == val2) ? null : val1
0364: .subtract(val2);
0365: }
0366: };
0367:
0368: // -------------------------------------------------------------------------
0369:
0370: /** Subtract two doubles. */
0371: public static final Function.F2<Double, Double, Double> subtractFloat64 = new Function.F2<Double, Double, Double>() {
0372: public Double apply(Double val1, Double val2) {
0373: return (null == val1) || (null == val2) ? null : val1
0374: - val2;
0375: }
0376: };
0377:
0378: // -------------------------------------------------------------------------
0379:
0380: /** Subtract two floats. */
0381: public static final Function.F2<Float, Float, Float> subtractFloat32 = new Function.F2<Float, Float, Float>() {
0382: public Float apply(Float val1, Float val2) {
0383: return (null == val1) || (null == val2) ? null : val1
0384: - val2;
0385: }
0386: };
0387:
0388: // -------------------------------------------------------------------------
0389:
0390: /** Multiply two big integers. */
0391: public static final Function.F2<BigInteger, BigInteger, BigInteger> multiplyInt = new Function.F2<BigInteger, BigInteger, BigInteger>() {
0392: public BigInteger apply(BigInteger val1, BigInteger val2) {
0393: return (null == val1) || (null == val2) ? null : val1
0394: .multiply(val2);
0395: }
0396: };
0397:
0398: // -------------------------------------------------------------------------
0399:
0400: /** Multiply two doubles. */
0401: public static final Function.F2<Double, Double, Double> multiplyFloat64 = new Function.F2<Double, Double, Double>() {
0402: public Double apply(Double val1, Double val2) {
0403: return (null == val1) || (null == val2) ? null : val1
0404: * val2;
0405: }
0406: };
0407:
0408: // -------------------------------------------------------------------------
0409:
0410: /** Multiply two floats. */
0411: public static final Function.F2<Float, Float, Float> multiplyFloat32 = new Function.F2<Float, Float, Float>() {
0412: public Float apply(Float val1, Float val2) {
0413: return (null == val1) || (null == val2) ? null : val1
0414: * val2;
0415: }
0416: };
0417:
0418: // -------------------------------------------------------------------------
0419:
0420: /** Divide two big integers. */
0421: public static final Function.F2<BigInteger, BigInteger, BigInteger> divideInt = new Function.F2<BigInteger, BigInteger, BigInteger>() {
0422: public BigInteger apply(BigInteger val1, BigInteger val2) {
0423: return (null == val1) || (null == val2) ? null : val1
0424: .divide(val2);
0425: }
0426: };
0427:
0428: // -------------------------------------------------------------------------
0429:
0430: /** Divide two doubles. */
0431: public static final Function.F2<Double, Double, Double> divideFloat64 = new Function.F2<Double, Double, Double>() {
0432: public Double apply(Double val1, Double val2) {
0433: return (null == val1) || (null == val2) ? null : val1
0434: / val2;
0435: }
0436: };
0437:
0438: // -------------------------------------------------------------------------
0439:
0440: /** Divide two Floats. */
0441: public static final Function.F2<Float, Float, Float> divideFloat32 = new Function.F2<Float, Float, Float>() {
0442: public Float apply(Float val1, Float val2) {
0443: return (null == val1) || (null == val2) ? null : val1
0444: / val2;
0445: }
0446: };
0447:
0448: // -------------------------------------------------------------------------
0449:
0450: /** Determine the modulo of two big integers. */
0451: public static final Function.F2<BigInteger, BigInteger, BigInteger> modInt = new Function.F2<BigInteger, BigInteger, BigInteger>() {
0452: public BigInteger apply(BigInteger val1, BigInteger val2) {
0453: return (null == val1) || (null == val2) ? null : val1
0454: .mod(val2);
0455: }
0456: };
0457:
0458: // -------------------------------------------------------------------------
0459:
0460: /** Determine the modulo of two doubles. */
0461: public static final Function.F2<Double, Double, Double> modFloat64 = new Function.F2<Double, Double, Double>() {
0462: public Double apply(Double val1, Double val2) {
0463: return (null == val1) || (null == val2) ? null : val1
0464: % val2;
0465: }
0466: };
0467:
0468: // -------------------------------------------------------------------------
0469:
0470: /** Determine the modulo of two floats. */
0471: public static final Function.F2<Float, Float, Float> modFloat32 = new Function.F2<Float, Float, Float>() {
0472: public Float apply(Float val1, Float val2) {
0473: return (null == val1) || (null == val2) ? null : val1
0474: % val2;
0475: }
0476: };
0477:
0478: // =========================================================================
0479: // Bitwise operations
0480: // =========================================================================
0481:
0482: /** Bitwise negate a big integer. */
0483: public static final Function.F1<BigInteger, BigInteger> negateBits = new Function.F1<BigInteger, BigInteger>() {
0484: public BigInteger apply(BigInteger val) {
0485: return null == val ? null : val.not();
0486: }
0487: };
0488:
0489: // -------------------------------------------------------------------------
0490:
0491: /** Bitwise and two big integers. */
0492: public static final Function.F2<BigInteger, BigInteger, BigInteger> andBits = new Function.F2<BigInteger, BigInteger, BigInteger>() {
0493: public BigInteger apply(BigInteger val1, BigInteger val2) {
0494: return (null == val1) || (null == val2) ? null : val1
0495: .and(val2);
0496: }
0497: };
0498:
0499: // -------------------------------------------------------------------------
0500:
0501: /** Bitwise or two big integers. */
0502: public static final Function.F2<BigInteger, BigInteger, BigInteger> orBits = new Function.F2<BigInteger, BigInteger, BigInteger>() {
0503: public BigInteger apply(BigInteger val1, BigInteger val2) {
0504: return (null == val1) || (null == val2) ? null : val1
0505: .or(val2);
0506: }
0507: };
0508:
0509: // -------------------------------------------------------------------------
0510:
0511: /** Bitwise xor two big integers. */
0512: public static final Function.F2<BigInteger, BigInteger, BigInteger> xorBits = new Function.F2<BigInteger, BigInteger, BigInteger>() {
0513: public BigInteger apply(BigInteger val1, BigInteger val2) {
0514: return (null == val1) || (null == val2) ? null : val1
0515: .xor(val2);
0516: }
0517: };
0518:
0519: // -------------------------------------------------------------------------
0520:
0521: /** Shift left a big integer. */
0522: public static final Function.F2<BigInteger, BigInteger, BigInteger> shiftLeft = new Function.F2<BigInteger, BigInteger, BigInteger>() {
0523: public BigInteger apply(BigInteger val1, BigInteger val2) {
0524: return (null == val1) || (null == val2) ? null : val1
0525: .shiftLeft(toInt(val2));
0526: }
0527: };
0528:
0529: // -------------------------------------------------------------------------
0530:
0531: /** Shift right a big integer. */
0532: public static final Function.F2<BigInteger, BigInteger, BigInteger> shiftRight = new Function.F2<BigInteger, BigInteger, BigInteger>() {
0533: public BigInteger apply(BigInteger val1, BigInteger val2) {
0534: return (null == val1) || (null == val2) ? null : val1
0535: .shiftRight(toInt(val2));
0536: }
0537: };
0538:
0539: // -------------------------------------------------------------------------
0540:
0541: /** Convert an int to a float. */
0542: public static final Function.F1<Double, BigInteger> itof = new Function.F1<Double, BigInteger>() {
0543: public Double apply(BigInteger i) {
0544: return (null == i) ? null : i.doubleValue();
0545: }
0546: };
0547:
0548: // -------------------------------------------------------------------------
0549:
0550: /** Convert a float to an int . */
0551: public static final Function.F1<BigInteger, Double> ftoi = new Function.F1<BigInteger, Double>() {
0552: public BigInteger apply(Double d) {
0553: return (null == d) ? null : new BigInteger(d.toString());
0554: }
0555: };
0556:
0557: // =========================================================================
0558: // List operations
0559: // =========================================================================
0560:
0561: /** Cons a value onto a list. */
0562: @SuppressWarnings("unchecked")
0563: public static final Function.F2<Pair, Object, Pair> cons = new Function.F2<Pair, Object, Pair>() {
0564: public Pair apply(Object head, Pair tail) {
0565: return null == tail ? null : new Pair(head, tail);
0566: }
0567: };
0568:
0569: /** Cons a value onto a list. */
0570: public static final class Cons<T> implements
0571: Function.F2<Pair<T>, T, Pair<T>> {
0572: public Pair<T> apply(T head, Pair<T> tail) {
0573: return null == tail ? null : new Pair<T>(head, tail);
0574: }
0575: }
0576:
0577: /**
0578: * Magic cast wrapper for Primitives.cons
0579: *
0580: * @param head The head of the pair.
0581: * @param p The tail of the pair.
0582: * @return The consed pair.
0583: */
0584: @SuppressWarnings("unchecked")
0585: public static final <T> Pair<T> wrapCons(T head, Pair<T> p) {
0586: return Primitives.cons.apply(head, p);
0587: }
0588:
0589: // -------------------------------------------------------------------------
0590:
0591: /** Determine whether a list is empty. */
0592: public static final Function.F1<Boolean, Pair<?>> isEmpty = new Function.F1<Boolean, Pair<?>>() {
0593: public Boolean apply(Pair<?> list) {
0594: return null == list ? null : list.isEmpty();
0595: }
0596: };
0597:
0598: // -------------------------------------------------------------------------
0599:
0600: /** Get a list's head. */
0601: public static final Function.F1<Object, Pair<?>> head = new Function.F1<Object, Pair<?>>() {
0602: public Object apply(Pair<?> list) {
0603: return (null == list) || (list.isEmpty()) ? null : list
0604: .head();
0605: }
0606: };
0607:
0608: /** Get a list's head. */
0609: public static final class Head<T> implements
0610: Function.F1<T, Pair<T>> {
0611: public T apply(Pair<T> list) {
0612: return (null == list) || (list.isEmpty()) ? null : list
0613: .head();
0614: }
0615: }
0616:
0617: /**
0618: * Magic cast wrapper for head
0619: *
0620: * @param p The pair.
0621: * @return The head of the pair.
0622: */
0623: @SuppressWarnings("unchecked")
0624: public static final <T> T wrapHead(Pair<T> p) {
0625: return (T) Primitives.head.apply(p);
0626: }
0627:
0628: // -------------------------------------------------------------------------
0629:
0630: /** Get a list's tail. */
0631: public static final Function.F1<Pair<?>, Pair<?>> tail = new Function.F1<Pair<?>, Pair<?>>() {
0632: public Pair<?> apply(Pair<?> list) {
0633: return (null == list) || (list.isEmpty()) ? null : list
0634: .tail();
0635: }
0636: };
0637:
0638: /** Get a list's tail. */
0639: public static final class Tail<T> implements
0640: Function.F1<Pair<T>, Pair<T>> {
0641: public Pair<T> apply(Pair<T> list) {
0642: return (null == list) || (list.isEmpty()) ? null : list
0643: .tail();
0644: }
0645: }
0646:
0647: /**
0648: * Magic cast wrapper for Primitives.tail
0649: *
0650: * @param p The pair.
0651: * @return The tail of the pair.
0652: */
0653: @SuppressWarnings("unchecked")
0654: public static final <T> Pair<T> wrapTail(Pair<T> p) {
0655: return (Pair<T>) Primitives.tail.apply(p);
0656: }
0657:
0658: // -------------------------------------------------------------------------
0659:
0660: /** Get a list's length. */
0661: public static final Function.F1<BigInteger, Pair<?>> length = new Function.F1<BigInteger, Pair<?>>() {
0662: public BigInteger apply(Pair<?> list) {
0663: return null == list ? null : BigInteger
0664: .valueOf(list.size());
0665: }
0666: };
0667:
0668: // -------------------------------------------------------------------------
0669:
0670: /** Get a list's nth element. */
0671: public static final Function.F2<Object, Pair<?>, BigInteger> nth = new Function.F2<Object, Pair<?>, BigInteger>() {
0672: public Object apply(Pair<?> list, BigInteger index) {
0673: return (null == list) || (null == index) ? null : list
0674: .get(toInt(index));
0675: }
0676: };
0677:
0678: /** Get a list's nth element. */
0679: public static final class Nth<T> implements
0680: Function.F2<T, Pair<T>, BigInteger> {
0681: public T apply(Pair<T> list, BigInteger index) {
0682: return (null == list) || (null == index) ? null : list
0683: .get(toInt(index));
0684: }
0685: }
0686:
0687: // -------------------------------------------------------------------------
0688:
0689: /** Determine whether a list contains an element. */
0690: public static final Function.F2<Boolean, Object, Pair<?>> contains = new Function.F2<Boolean, Object, Pair<?>>() {
0691: public Boolean apply(Object elem, Pair<?> list) {
0692: return (null == elem) || (null == list) ? null : list
0693: .contains(elem);
0694: }
0695: };
0696:
0697: // -------------------------------------------------------------------------
0698:
0699: /** Determine whether a list element satisfies a predicate. */
0700: @SuppressWarnings("unchecked")
0701: public static final Function.F2<Boolean, Function.F1<Boolean, Object>, Pair> exists = new Function.F2<Boolean, Function.F1<Boolean, Object>, Pair>() {
0702: public Boolean apply(Function.F1<Boolean, Object> pred,
0703: Pair list) {
0704: return ((null == pred) || (null == list)) ? null : Function
0705: .matchesOne(pred, list);
0706: }
0707: };
0708:
0709: /** Determine whether a list element satisfies a predicate. */
0710: public static final class Exists<T>
0711: implements
0712: Function.F2<Boolean, Function.F1<Boolean, ? super T>, Pair<T>> {
0713: public Boolean apply(Function.F1<Boolean, ? super T> pred,
0714: Pair<T> list) {
0715: return (null == pred) || (null == list) ? null : Function
0716: .matchesOne(pred, list);
0717: }
0718: }
0719:
0720: // -------------------------------------------------------------------------
0721:
0722: /** Iterate a function over a list. */
0723: @SuppressWarnings("unchecked")
0724: public static final Function.F2<Object, Function.F1<Object, Object>, Pair> iter = new Function.F2<Object, Function.F1<Object, Object>, Pair>() {
0725: public Object apply(Function.F1<Object, Object> func, Pair list) {
0726: if ((null == func) || (null == list))
0727: return null;
0728: Function.iterate(func, list);
0729: return null;
0730: }
0731: };
0732:
0733: /** Iterate a function over a list. */
0734: public static final class Iter<T, U> implements
0735: Function.F2<T, Function.F1<T, ? super U>, Pair<U>> {
0736: public T apply(Function.F1<T, ? super U> func, Pair<U> list) {
0737: if ((null == func) || (null == list))
0738: return null;
0739: Function.iterate(func, list);
0740: return null;
0741: }
0742: }
0743:
0744: // -------------------------------------------------------------------------
0745:
0746: /** Map a function over a list. */
0747: @SuppressWarnings("unchecked")
0748: public static final Function.F2<Pair, Function.F1<Object, Object>, Pair> map = new Function.F2<Pair, Function.F1<Object, Object>, Pair>() {
0749: public Pair apply(Function.F1<Object, Object> func, Pair list) {
0750: return (null == func) || (null == list) ? null : Function
0751: .map(func, list);
0752: }
0753: };
0754:
0755: /** Map a function over a list. */
0756: public static final class Map<T, U> implements
0757: Function.F2<Pair<T>, Function.F1<T, ? super U>, Pair<U>> {
0758: public Pair<T> apply(Function.F1<T, ? super U> func,
0759: Pair<U> list) {
0760: return (null == func) || (null == list) ? null : Function
0761: .map(func, list);
0762: }
0763: }
0764:
0765: // -------------------------------------------------------------------------
0766:
0767: /** Fold a list. */
0768: @SuppressWarnings("unchecked")
0769: public static final Function.F3<Object, Function.F2<Object, Object, Object>, Pair, Object> foldl = new Function.F3<Object, Function.F2<Object, Object, Object>, Pair, Object>() {
0770: public Object apply(Function.F2<Object, Object, Object> f,
0771: Pair l, Object s) {
0772: return (null == f) || (null == l) || (null == s) ? null
0773: : Function.foldl(f, s, l);
0774: }
0775: };
0776:
0777: /** Fold a list. */
0778: public static final class FoldLeft<T, U> implements
0779: Function.F3<T, Function.F2<T, ? super U, T>, Pair<U>, T> {
0780: public T apply(Function.F2<T, ? super U, T> f, Pair<U> l, T s) {
0781: return (null == f) || (null == l) || (null == s) ? null
0782: : Function.foldl(f, s, l);
0783: }
0784: }
0785:
0786: // -------------------------------------------------------------------------
0787:
0788: /** Non-destructively append two lists. */
0789: @SuppressWarnings("unchecked")
0790: public static final Function.F2<Pair, Pair, Pair> append = new Function.F2<Pair, Pair, Pair>() {
0791: public Pair apply(Pair list1, Pair list2) {
0792: return (null == list1) || (null == list2) ? null : list1
0793: .append(list2);
0794: }
0795: };
0796:
0797: /** Non-destructively append two lists. */
0798: public static final class Append<T> implements
0799: Function.F2<Pair<T>, Pair<T>, Pair<T>> {
0800: public Pair<T> apply(Pair<T> list1, Pair<T> list2) {
0801: return (null == list1) || (null == list2) ? null : list1
0802: .append(list2);
0803: }
0804: }
0805:
0806: /**
0807: * Magic cast wrapper for append
0808: *
0809: * @param l The left pair.
0810: * @param r The right pair.
0811: * @return The concatenation of the two pairs.
0812: */
0813: @SuppressWarnings("unchecked")
0814: public static final <T> Pair<T> wrapAppend(Pair<T> l, Pair<T> r) {
0815: return Primitives.append.apply(l, r);
0816: }
0817:
0818: /**
0819: * Find an object in a pair.
0820: *
0821: * @param o The object to find.
0822: * @param p The list.
0823: * @return The object or <code>null</code> if the list does not
0824: * contain the object.
0825: */
0826: public static final <T> T findInPair(Object o, Pair<T> p) {
0827: if ((null == o) || (null == p))
0828: return null;
0829:
0830: for (T t : p) {
0831: if (o.equals(t))
0832: return t;
0833: }
0834:
0835: return null;
0836: }
0837:
0838: /**
0839: * Copy a list.
0840: *
0841: * @param left The list to copy.
0842: * @return The copy.
0843: */
0844: @SuppressWarnings("unchecked")
0845: static public final <T, R> Pair<T> copyPair(Pair<R> left) {
0846: if (null == left)
0847: return null;
0848: Pair<T> result = Pair.empty();
0849: for (Iterator<R> iter = left.iterator(); iter.hasNext();) {
0850: result = result.append(new Pair<T>((T) iter.next()));
0851: }
0852: return result;
0853: }
0854:
0855: /**
0856: * Remove an object from a list.
0857: *
0858: * @param o The object to remove.
0859: * @param left The list to remove an object from.
0860: * @return The resulted list.
0861: */
0862: static public final <T> Pair<T> removeFromPair(Object o,
0863: Pair<T> left) {
0864: if (null == left)
0865: return null;
0866: Pair<T> result = Pair.empty();
0867:
0868: for (Iterator<T> iter = left.iterator(); iter.hasNext();) {
0869: T t = iter.next();
0870: if (o.equals(t))
0871: continue;
0872: result = result.append(new Pair<T>(t));
0873: }
0874:
0875: return result;
0876: }
0877:
0878: // -------------------------------------------------------------------------
0879:
0880: /** Determine the set union of two lists. */
0881: @SuppressWarnings("unchecked")
0882: public static final Function.F2<Pair, Pair, Pair> union = new Function.F2<Pair, Pair, Pair>() {
0883: public Pair apply(Pair list1, Pair list2) {
0884: return (null == list1) || (null == list2) ? null : list1
0885: .combine(list2);
0886: }
0887: };
0888:
0889: /** Determine the set union of two lists. */
0890: public static final class Union<T> implements
0891: Function.F2<Pair<T>, Pair<T>, Pair<T>> {
0892: public Pair<T> apply(Pair<T> list1, Pair<T> list2) {
0893: return (null == list1) || (null == list2) ? null : list1
0894: .combine(list2);
0895: }
0896: }
0897:
0898: /**
0899: * Magic cast wrapper for Primitives.union
0900: *
0901: * @param l The left pair.
0902: * @param r The right pair.
0903: * @return The union of the two pairs.
0904: */
0905: @SuppressWarnings("unchecked")
0906: public static final <T> Pair<T> wrapUnion(Pair<T> l, Pair<T> r) {
0907: return Primitives.union.apply(l, r);
0908: }
0909:
0910: // -------------------------------------------------------------------------
0911:
0912: /** Determine the set intersection of two lists. */
0913: @SuppressWarnings("unchecked")
0914: public static final Function.F2<Pair, Pair, Pair> intersection = new Function.F2<Pair, Pair, Pair>() {
0915: public Pair apply(Pair list1, Pair list2) {
0916: return (null == list1) || (null == list2) ? null : list1
0917: .intersect(list2);
0918: }
0919: };
0920:
0921: /** Determine the set intersection of two lists. */
0922: public static final class Intersection<T> implements
0923: Function.F2<Pair<T>, Pair<T>, Pair<T>> {
0924: public Pair<T> apply(Pair<T> list1, Pair<T> list2) {
0925: return (null == list1) || (null == list2) ? null : list1
0926: .intersect(list2);
0927: }
0928: }
0929:
0930: // -------------------------------------------------------------------------
0931:
0932: /** Determine the set subtraction of two lists. */
0933: @SuppressWarnings("unchecked")
0934: public static final Function.F2<Pair, Pair, Pair> subtraction = new Function.F2<Pair, Pair, Pair>() {
0935: public Pair apply(Pair list1, Pair list2) {
0936: return (null == list1) || (null == list2) ? null : list1
0937: .subtract(list2);
0938: }
0939: };
0940:
0941: /** Determine the set subtraction of two lists. */
0942: public static final class Subtraction<T> implements
0943: Function.F2<Pair<T>, Pair<T>, Pair<T>> {
0944: public Pair<T> apply(Pair<T> list1, Pair<T> list2) {
0945: return (null == list1) || (null == list2) ? null : list1
0946: .subtract(list2);
0947: }
0948: }
0949:
0950: // =========================================================================
0951: // String operations
0952: // =========================================================================
0953:
0954: /** Concatenate two strings. */
0955: public static final Function.F2<String, String, String> concat = new Function.F2<String, String, String>() {
0956: public String apply(String s1, String s2) {
0957: return (null == s1) || (null == s2) ? null : s1 + s2;
0958: }
0959: };
0960:
0961: // -------------------------------------------------------------------------
0962:
0963: /** Get a string's size */
0964: public static final Function.F1<BigInteger, String> ssize = new Function.F1<BigInteger, String>() {
0965: public BigInteger apply(String s) {
0966: return null == s ? null : BigInteger.valueOf(s.length());
0967: }
0968: };
0969:
0970: // -------------------------------------------------------------------------
0971:
0972: /** Convert a string to a big integer. */
0973: public static final Function.F2<BigInteger, String, BigInteger> stoi = new Function.F2<BigInteger, String, BigInteger>() {
0974: public BigInteger apply(String s, BigInteger radix) {
0975: return null == s ? null : new BigInteger(s, radix
0976: .intValue());
0977: }
0978: };
0979:
0980: // -------------------------------------------------------------------------
0981:
0982: /** Check if the first string starts with the second. */
0983: public static final Function.F2<Boolean, String, String> startsWith = new Function.F2<Boolean, String, String>() {
0984: public Boolean apply(String s, String prefix) {
0985: return (null == s) || (null == prefix) ? null : s
0986: .startsWith(prefix);
0987: }
0988: };
0989:
0990: // -------------------------------------------------------------------------
0991:
0992: /** Check if the first string starts with the second. */
0993: public static final Function.F2<Boolean, String, String> startsWithi = new Function.F2<Boolean, String, String>() {
0994: public Boolean apply(String s, String prefix) {
0995: return (null == s) || (null == prefix) ? null : s
0996: .toLowerCase().startsWith(prefix.toLowerCase());
0997: }
0998: };
0999:
1000: // -------------------------------------------------------------------------
1001:
1002: /** Check if the first string ends with the second. */
1003: public static final Function.F2<Boolean, String, String> endsWith = new Function.F2<Boolean, String, String>() {
1004: public Boolean apply(String s, String suffix) {
1005: return (null == s) || (null == suffix) ? null : s
1006: .endsWith(suffix);
1007: }
1008: };
1009:
1010: // -------------------------------------------------------------------------
1011:
1012: /** Check if the first string ends with - ignoring case */
1013: public static final Function.F2<Boolean, String, String> endsWithi = new Function.F2<Boolean, String, String>() {
1014: public Boolean apply(String s, String suffix) {
1015: return (null == s) || (null == suffix) ? null : s
1016: .toLowerCase().endsWith(suffix.toLowerCase());
1017: }
1018: };
1019:
1020: // -------------------------------------------------------------------------
1021:
1022: /** Join strings */
1023: public static final Function.F1<String, Pair<String>> joinStrings = new Function.F1<String, Pair<String>>() {
1024: public String apply(Pair<String> slist) {
1025: if (null == slist)
1026: return null;
1027:
1028: String result = "";
1029: for (Iterator<String> iter = slist.iterator(); iter
1030: .hasNext();) {
1031: result += iter.next();
1032: }
1033: return result.trim();
1034: }
1035: };
1036:
1037: // -------------------------------------------------------------------------
1038:
1039: /** Get the substrng starting at the specified index */
1040: public static final Function.F2<String, String, BigInteger> substring = new Function.F2<String, String, BigInteger>() {
1041: public String apply(String s, BigInteger i) {
1042: return (null == s) || (null == i) ? null : s.substring(i
1043: .intValue());
1044: }
1045: };
1046:
1047: // -------------------------------------------------------------------------
1048:
1049: /** Get the substrng at the specified range */
1050: public static final Function.F3<String, String, BigInteger, BigInteger> substring2 = new Function.F3<String, String, BigInteger, BigInteger>() {
1051: public String apply(String s, BigInteger start, BigInteger end) {
1052: return (null == s) || (null == start) || (null == end) ? null
1053: : s.substring(start.intValue(), end.intValue());
1054: }
1055: };
1056:
1057: // -------------------------------------------------------------------------
1058:
1059: /** Convert a string to a double. */
1060: public static final Function.F1<Double, String> stof = new Function.F1<Double, String>() {
1061: public Double apply(String s) {
1062: return null == s ? null : Double.valueOf(s);
1063: }
1064: };
1065:
1066: /** Convert an interger to a string. */
1067: public static final Function.F1<String, BigInteger> itos = new Function.F1<String, BigInteger>() {
1068: public String apply(BigInteger i) {
1069: return null == i ? null : i.toString();
1070: }
1071: };
1072:
1073: /** Convert a float to a string. */
1074: public static final Function.F1<String, Double> ftos = new Function.F1<String, Double>() {
1075: public String apply(Double f) {
1076: return null == f ? null : f.toString();
1077: }
1078: };
1079:
1080: // =========================================================================
1081: // Nonce operations
1082: // =========================================================================
1083:
1084: /** The nonce counter. */
1085: protected static BigInteger nonceCounter = BigInteger.ZERO;
1086:
1087: /** Create a nonce. The implementation is not thread-safe. */
1088: public static final Function.F0<BigInteger> nonce = new Function.F0<BigInteger>() {
1089: public BigInteger apply() {
1090: nonceCounter = nonceCounter.add(BigInteger.ONE);
1091: return nonceCounter;
1092: }
1093: };
1094:
1095: // =========================================================================
1096: // Debug operations
1097: // =========================================================================
1098:
1099: /** Trace a value. */
1100: public static final Function.F1<Object, Object> trace = new Function.F1<Object, Object>() {
1101: public Object apply(Object o) {
1102: trace("", o);
1103: return o;
1104: }
1105: };
1106:
1107: /** Trace a value. */
1108: public static final class Trace<T> implements Function.F1<T, T> {
1109: public T apply(T val) {
1110: trace("", val);
1111: return val;
1112: }
1113: }
1114:
1115: // -------------------------------------------------------------------------
1116:
1117: /** Trace a value. */
1118: public static final Function.F2<Object, String, Object> trace2 = new Function.F2<Object, String, Object>() {
1119: public Object apply(String msg, Object o) {
1120: trace(msg, o);
1121: return o;
1122: }
1123: };
1124:
1125: /** Trace a value. */
1126: public static final class Trace2<T> implements
1127: Function.F2<T, String, T> {
1128: public T apply(String msg, T val) {
1129: trace(msg, val);
1130: return val;
1131: }
1132: }
1133:
1134: // =========================================================================
1135: // node manipulation functions
1136: // =========================================================================
1137:
1138: /** The typical function for annotating nodes. */
1139: public static final Function.F3<Object, Node, String, Object> annotate = new Function.F3<Object, Node, String, Object>() {
1140: public final Object apply(Node n, String name, Object annotation) {
1141: if ((null == n) || (null == name) || (null == annotation))
1142: return null;
1143: n.setProperty(name, annotation);
1144: return annotation;
1145: }
1146: };
1147:
1148: // -------------------------------------------------------------------------
1149:
1150: /** The typical function for annotating lists of nodes. */
1151: public static final Function.F3<Object, Pair<Node>, String, Object> annotateList = new Function.F3<Object, Pair<Node>, String, Object>() {
1152: public final Object apply(Pair<Node> p, String name,
1153: Object annotation) {
1154: for (Iterator<Node> iter = p.iterator(); iter.hasNext();) {
1155: Node n = iter.next();
1156: if (null == n) {
1157: continue;
1158: }
1159: n.setProperty(name, annotation);
1160: }
1161: return annotation;
1162: }
1163: };
1164:
1165: // -------------------------------------------------------------------------
1166:
1167: /** The typical function for getting node annotation */
1168: public static final Function.F2<Object, Node, String> getAnnotation = new Function.F2<Object, Node, String>() {
1169: public final Object apply(Node n, String name) {
1170: if ((null == n) || (null == name))
1171: return null;
1172: return n.hasProperty(name) ? n.getProperty(name) : null;
1173: }
1174: };
1175:
1176: // -------------------------------------------------------------------------
1177:
1178: /** The typical function for checking if a node has an annotation */
1179: public static final Function.F2<Boolean, Node, String> hasAnnotation = new Function.F2<Boolean, Node, String>() {
1180: public final Boolean apply(Node n, String name) {
1181: return (null == n) || (null == name) ? null : n
1182: .hasProperty(name);
1183: }
1184: };
1185:
1186: // -------------------------------------------------------------------------
1187:
1188: /** The function to get the name of a node. */
1189: public static final Function.F1<String, Object> node_name = new Function.F1<String, Object>() {
1190: public final String apply(Object n) {
1191: if (null == n) {
1192: return "?";
1193: }
1194: if (!(n instanceof Node)) {
1195: throw new IllegalStateException(
1196: "calling nodeName on non-node");
1197: }
1198: return ((Node) n).getName();
1199: }
1200: };
1201:
1202: // =========================================================================
1203: // Map operations
1204: // =========================================================================
1205: /** A get function to access the hash table. */
1206: public static final Function.F2<Object, Object, Hashtable<Object, Object>> get = new Function.F2<Object, Object, Hashtable<Object, Object>>() {
1207: public final Object apply(Object o,
1208: Hashtable<Object, Object> hashTable) {
1209: return null == o ? null : hashTable.get(o);
1210: }
1211: };
1212:
1213: /** A put function to access the hash table. */
1214: public static final Function.F3<Void, Object, Object, Hashtable<Object, Object>> put = new Function.F3<Void, Object, Object, Hashtable<Object, Object>>() {
1215: public final Void apply(Object o, Object ob,
1216: Hashtable<Object, Object> hashTable) {
1217: if (null == o || null == ob)
1218: return null;
1219: hashTable.put(o, ob);
1220: return null;
1221: }
1222: };
1223:
1224: // --------------------------------------------------------------------------
1225:
1226: /**
1227: * Get children of a node by indice.
1228: *
1229: * @param n The node to get children.
1230: * @param from The start index.
1231: * @param to The end index.
1232: * @return null if the indice are out of range, otherwise return a
1233: * pair of nodes.
1234: */
1235: @SuppressWarnings("unchecked")
1236: public static final <T> Pair<T> getChildren(Node n, int from, int to) {
1237: if (to > n.size()) {
1238: throw new RuntimeException("bad index for get children");
1239: }
1240:
1241: Pair<T> p = Pair.empty();
1242:
1243: if (n.size() > from) {
1244: p = new Pair<T>((T) n.get(from));
1245: }
1246:
1247: for (int i = from + 1; i < to; i++) {
1248: p = p.append(new Pair<T>((T) n.get(i)));
1249: }
1250:
1251: return p;
1252: }
1253:
1254: // =========================================================================
1255: // Primitive tests and name translation
1256: // =========================================================================
1257:
1258: /** The names of functions that are primitive functions. */
1259: private static Set<String> PRIMITIVE_FUNCTIONS;
1260:
1261: static {
1262: PRIMITIVE_FUNCTIONS = new HashSet<String>();
1263:
1264: PRIMITIVE_FUNCTIONS.add("nonce");
1265: PRIMITIVE_FUNCTIONS.add("isBottom");
1266: PRIMITIVE_FUNCTIONS.add("isNotBottom");
1267: PRIMITIVE_FUNCTIONS.add("negateInt");
1268: PRIMITIVE_FUNCTIONS.add("negateFloat64");
1269: PRIMITIVE_FUNCTIONS.add("negateBits");
1270: PRIMITIVE_FUNCTIONS.add("andBits");
1271: PRIMITIVE_FUNCTIONS.add("orBits");
1272: PRIMITIVE_FUNCTIONS.add("xorBits");
1273: PRIMITIVE_FUNCTIONS.add("shiftLeft");
1274: PRIMITIVE_FUNCTIONS.add("shiftRight");
1275: PRIMITIVE_FUNCTIONS.add("cons");
1276: PRIMITIVE_FUNCTIONS.add("isEmpty");
1277: PRIMITIVE_FUNCTIONS.add("head");
1278: PRIMITIVE_FUNCTIONS.add("tail");
1279: PRIMITIVE_FUNCTIONS.add("length");
1280: PRIMITIVE_FUNCTIONS.add("nth");
1281: PRIMITIVE_FUNCTIONS.add("containts");
1282: PRIMITIVE_FUNCTIONS.add("exists");
1283: PRIMITIVE_FUNCTIONS.add("append");
1284: PRIMITIVE_FUNCTIONS.add("union");
1285: PRIMITIVE_FUNCTIONS.add("intersection");
1286: PRIMITIVE_FUNCTIONS.add("subtraction");
1287: PRIMITIVE_FUNCTIONS.add("concat");
1288: PRIMITIVE_FUNCTIONS.add("stoi");
1289: PRIMITIVE_FUNCTIONS.add("stof");
1290: PRIMITIVE_FUNCTIONS.add("trace");
1291: PRIMITIVE_FUNCTIONS.add("trace2");
1292: PRIMITIVE_FUNCTIONS.add("ssize");
1293: PRIMITIVE_FUNCTIONS.add("ftoi");
1294: PRIMITIVE_FUNCTIONS.add("joinStrings");
1295: PRIMITIVE_FUNCTIONS.add("absInt");
1296: PRIMITIVE_FUNCTIONS.add("absFloat64");
1297: PRIMITIVE_FUNCTIONS.add("startsWith");
1298: PRIMITIVE_FUNCTIONS.add("startsWithi");
1299: PRIMITIVE_FUNCTIONS.add("endsWith");
1300: PRIMITIVE_FUNCTIONS.add("endsWithi");
1301: PRIMITIVE_FUNCTIONS.add("substring");
1302: PRIMITIVE_FUNCTIONS.add("substring2");
1303: PRIMITIVE_FUNCTIONS.add("iter");
1304: PRIMITIVE_FUNCTIONS.add("foldl");
1305: PRIMITIVE_FUNCTIONS.add("annotate");
1306: PRIMITIVE_FUNCTIONS.add("annotateList");
1307: PRIMITIVE_FUNCTIONS.add("node_name");
1308: PRIMITIVE_FUNCTIONS.add("getAnnotation");
1309: PRIMITIVE_FUNCTIONS.add("hasAnnotation");
1310: PRIMITIVE_FUNCTIONS.add("map");
1311: }
1312:
1313: /**
1314: * Check if a function is a primitive function
1315: *
1316: * @param name The function name
1317: * @return true or false
1318: */
1319: public static boolean isPrimitive(String name) {
1320: return PRIMITIVE_FUNCTIONS.contains(name);
1321: }
1322:
1323: /** The mapping from Typical primitives to actual primitive names. */
1324: private static java.util.Map<String, String> PRIMITIVE_NAMES;
1325:
1326: static {
1327: PRIMITIVE_NAMES = new HashMap<String, String>();
1328:
1329: PRIMITIVE_NAMES.put("is_bottom", "isBottom");
1330: PRIMITIVE_NAMES.put("is_not_bottom", "isNotBottom");
1331: PRIMITIVE_NAMES.put("negate_int", "negateInt");
1332: PRIMITIVE_NAMES.put("negate_float", "negateFloat64");
1333: PRIMITIVE_NAMES.put("negate_bits", "negateBits");
1334: PRIMITIVE_NAMES.put("and_bits", "andBits");
1335: PRIMITIVE_NAMES.put("or_bits", "orBits");
1336: PRIMITIVE_NAMES.put("xor_bits", "xorBits");
1337: PRIMITIVE_NAMES.put("shift_left", "shiftLeft");
1338: PRIMITIVE_NAMES.put("shift_right", "shiftRight");
1339: PRIMITIVE_NAMES.put("is_empty", "isEmpty");
1340: PRIMITIVE_NAMES.put("mem", "contains");
1341: PRIMITIVE_NAMES.put("not_bottom", "notBottom");
1342: PRIMITIVE_NAMES.put("is_defined", "isDefined");
1343: PRIMITIVE_NAMES.put("lookup_locally", "lookupLocally");
1344: PRIMITIVE_NAMES.put("is_defined_locally", "isDefinedLocally");
1345: PRIMITIVE_NAMES.put("lookup_node", "lookupNode");
1346: PRIMITIVE_NAMES.put("define_node", "defineNode");
1347: PRIMITIVE_NAMES.put("annotate_list", "annotateList");
1348: PRIMITIVE_NAMES.put("has_annotation", "hasAnnotation");
1349: PRIMITIVE_NAMES.put("get_annotation", "getAnnotation");
1350: PRIMITIVE_NAMES.put("fresh_name", "freshName");
1351: PRIMITIVE_NAMES.put("remove_last", "removeLast");
1352: PRIMITIVE_NAMES.put("abs_int", "absInt");
1353: PRIMITIVE_NAMES.put("abs_float", "absFloat64");
1354: PRIMITIVE_NAMES.put("join_strings", "joinStrings");
1355: PRIMITIVE_NAMES.put("starts_with", "startsWith");
1356: PRIMITIVE_NAMES.put("starts_withi", "startsWithi");
1357: PRIMITIVE_NAMES.put("ends_with", "endsWith");
1358: PRIMITIVE_NAMES.put("ends_withi", "endsWithi");
1359: PRIMITIVE_NAMES.put("node_type", "nodeType");
1360: PRIMITIVE_NAMES.put("is_big_endian", "IS_BIG_ENDIAN");
1361: PRIMITIVE_NAMES.put("void_size", "VOID_SIZE");
1362: PRIMITIVE_NAMES.put("pointer_size", "POINTER_SIZE");
1363: PRIMITIVE_NAMES.put("pointer_align", "POINTER_ALIGN");
1364: PRIMITIVE_NAMES.put("ptrdiff_rank", "PTRDIFF_RANK");
1365: PRIMITIVE_NAMES.put("sizeof_rank", "SIZEOF_RANK");
1366: PRIMITIVE_NAMES.put("ptrdiff_size", "PTRDIFF_SIZE");
1367: PRIMITIVE_NAMES.put("sizeof_size", "SIZEOF_SIZE");
1368: PRIMITIVE_NAMES.put("array_max", "ARRAY_MAX");
1369: PRIMITIVE_NAMES.put("is_char_signed", "IS_CHAR_SIGNED");
1370: PRIMITIVE_NAMES.put("char_bits", "CHAR_BITS");
1371: PRIMITIVE_NAMES.put("char_min", "CHAR_MIN");
1372: PRIMITIVE_NAMES.put("char_max", "CHAR_MAX");
1373: PRIMITIVE_NAMES.put("char_mod", "CHAR_MOD");
1374: PRIMITIVE_NAMES.put("uchar_mac", "UCHAR_MAX");
1375: PRIMITIVE_NAMES.put("uchar_mod", "UCHAR_MOD");
1376: PRIMITIVE_NAMES.put("is_wchar_signed", "IS_WCHAR_SIGNED");
1377: PRIMITIVE_NAMES.put("wchar_rank", "WCHAR_RANK");
1378: PRIMITIVE_NAMES.put("wchar_size", "WCHAR_SIZE");
1379: PRIMITIVE_NAMES.put("short_size", "SHORT_SIZE");
1380: PRIMITIVE_NAMES.put("short_align", "SHORT_ALIGN");
1381: PRIMITIVE_NAMES.put("short_bits", "SHORT_BITS");
1382: PRIMITIVE_NAMES.put("short_min", "SHORT_MIN");
1383: PRIMITIVE_NAMES.put("short_max", "SHORT_MAX");
1384: PRIMITIVE_NAMES.put("short_mod", "SHORT_MOD");
1385: PRIMITIVE_NAMES.put("ushort_max", "USHORT_MAX");
1386: PRIMITIVE_NAMES.put("ushort_mod", "USHORT_MOD");
1387: PRIMITIVE_NAMES.put("is_int_signed", "IS_INT_SIGNED");
1388: PRIMITIVE_NAMES.put("int_size", "INT_SIZE");
1389: PRIMITIVE_NAMES.put("int_align", "INT_ALIGN");
1390: PRIMITIVE_NAMES.put("int_bits", "INT_BITS");
1391: PRIMITIVE_NAMES.put("int_min", "INT_MIN");
1392: PRIMITIVE_NAMES.put("int_max", "INT_MAX");
1393: PRIMITIVE_NAMES.put("int_mod", "INT_MOD");
1394: PRIMITIVE_NAMES.put("uint_max", "UINT_MAX");
1395: PRIMITIVE_NAMES.put("uint_mod", "UINT_MOD");
1396: PRIMITIVE_NAMES.put("long_size", "LONG_SIZE");
1397: PRIMITIVE_NAMES.put("long_align", "LONG_ALIGN");
1398: PRIMITIVE_NAMES.put("long_bits", "LONG_BITS");
1399: PRIMITIVE_NAMES.put("long_min", "LONG_MIN");
1400: PRIMITIVE_NAMES.put("long_max", "LONG_MAX");
1401: PRIMITIVE_NAMES.put("long_mod", "LONG_MOD");
1402: PRIMITIVE_NAMES.put("ulong_max", "ULONG_MAX");
1403: PRIMITIVE_NAMES.put("ulong_mod", "ULONG_MOD");
1404: PRIMITIVE_NAMES.put("long_long_size", "LONG_LONG_SIZE");
1405: PRIMITIVE_NAMES.put("long_long_align", "LONG_LONG_ALIGN");
1406: PRIMITIVE_NAMES.put("long_long_bits", "LONG_LONG_BITS");
1407: PRIMITIVE_NAMES.put("long_long_min", "LONG_LONG_MIN");
1408: PRIMITIVE_NAMES.put("long_long_max", "LONG_LONG_MAX");
1409: PRIMITIVE_NAMES.put("long_long_mod", "LONG_LONG_MOD");
1410: PRIMITIVE_NAMES.put("ulong_long_max", "ULONG_LONG_MAX");
1411: PRIMITIVE_NAMES.put("ulong_long_mod", "ULONG_LONG_MOD");
1412: PRIMITIVE_NAMES.put("float_size", "FLOAT_SIZE");
1413: PRIMITIVE_NAMES.put("float_align", "FLOAT_ALIGN");
1414: PRIMITIVE_NAMES.put("double_size", "DOUBLE_SIZE");
1415: PRIMITIVE_NAMES.put("double_align", "DOUBLE_ALIGN");
1416: PRIMITIVE_NAMES.put("long_double_size", "LONG_DOUBLE_SIZE");
1417: PRIMITIVE_NAMES.put("long_double_align", "LONG_DOUBLE_ALIGN");
1418: }
1419:
1420: /**
1421: * Convert a name from ML style to Java style.
1422: *
1423: * @param name The name to convert.
1424: * @return The converted name.
1425: */
1426: public static String convertName(String name) {
1427: return PRIMITIVE_NAMES.containsKey(name) ? PRIMITIVE_NAMES
1428: .get(name) : name;
1429: }
1430:
1431: /** The names of types that are also integers. */
1432: private static Set<String> INTEGER_TYPES;
1433:
1434: static {
1435: INTEGER_TYPES = new HashSet<String>();
1436:
1437: INTEGER_TYPES.add("VOID_SIZE");
1438: INTEGER_TYPES.add("POINTER_SIZE");
1439: INTEGER_TYPES.add("POINTER_ALIGN");
1440: INTEGER_TYPES.add("PTRDIFF_RANK");
1441: INTEGER_TYPES.add("SIZEOF_RANK");
1442: INTEGER_TYPES.add("PTRDIFF_SIZE");
1443: INTEGER_TYPES.add("SIZEOF_SIZE");
1444: INTEGER_TYPES.add("CHAR_BITS");
1445: INTEGER_TYPES.add("WCHAR_RANK");
1446: INTEGER_TYPES.add("WCHAR_SIZE");
1447: INTEGER_TYPES.add("SHORT_SIZE");
1448: INTEGER_TYPES.add("SHORT_ALIGN");
1449: INTEGER_TYPES.add("SHORT_BITS");
1450: INTEGER_TYPES.add("INT_SIZE");
1451: INTEGER_TYPES.add("INT_ALIGN");
1452: INTEGER_TYPES.add("INT_BITS");
1453: INTEGER_TYPES.add("LONG_SIZE");
1454: INTEGER_TYPES.add("LONG_ALIGN");
1455: INTEGER_TYPES.add("LONG_BITS");
1456: INTEGER_TYPES.add("LONG_LONG_SIZE");
1457: INTEGER_TYPES.add("LONG_LONG_ALIGN");
1458: INTEGER_TYPES.add("LONG_LONG_BITS");
1459: INTEGER_TYPES.add("FLOAT_SIZE");
1460: INTEGER_TYPES.add("FLOAT_ALIGN");
1461: INTEGER_TYPES.add("DOUBLE_SIZE");
1462: INTEGER_TYPES.add("DOUBLE_ALIGN");
1463: INTEGER_TYPES.add("LONG_DOUBLE_SIZE");
1464: INTEGER_TYPES.add("LONG_DOUBLE_ALIGN");
1465: }
1466:
1467: /**
1468: * Check if a machine dependent constant has integer type
1469: *
1470: * @param name The name of the constant
1471: * @return <code>true</code> if that constant has integer type,
1472: * otherwise <code>false</code>
1473: */
1474: public static boolean hasIntegerType(String name) {
1475: return INTEGER_TYPES.contains(name);
1476: }
1477:
1478: }
|