001: package net.sf.saxon.value;
002:
003: import net.sf.saxon.expr.XPathContext;
004: import net.sf.saxon.om.FastStringBuffer;
005: import net.sf.saxon.trans.DynamicError;
006: import net.sf.saxon.trans.XPathException;
007: import net.sf.saxon.type.*;
008:
009: import java.util.regex.Matcher;
010: import java.util.regex.Pattern;
011:
012: /**
013: * Implementation of the xs:gYear data type
014: */
015:
016: public class GYearValue extends DateValue {
017:
018: private static Pattern regex = Pattern
019: .compile("(-?[0-9]+)(Z|[+-][0-9][0-9]:[0-9][0-9])?");
020:
021: public GYearValue() {
022: };
023:
024: public GYearValue(CharSequence value) throws XPathException {
025: Matcher m = regex.matcher(value);
026: if (!m.matches()) {
027: throw new DynamicError("Cannot convert '" + value
028: + "' to a gYear");
029: }
030: String base = m.group(1);
031: String tz = m.group(2);
032: String date = base + "-01-01" + (tz == null ? "" : tz);
033: setLexicalValue(date);
034: }
035:
036: public GYearValue(int year, int tz) {
037: this .year = year;
038: this .month = 1;
039: this .day = 1;
040: setTimezoneInMinutes(tz);
041: }
042:
043: /**
044: * Determine the data type of the expression
045: * @return Type.G_YEAR_TYPE,
046: * @param th
047: */
048:
049: public ItemType getItemType(TypeHierarchy th) {
050: return Type.G_YEAR_TYPE;
051: }
052:
053: /**
054: * Make a copy of this date, time, or dateTime value
055: */
056:
057: public CalendarValue copy() {
058: return new GYearValue(year, getTimezoneInMinutes());
059: }
060:
061: /**
062: * Convert to target data type
063: * @param requiredType an integer identifying the required atomic type
064: * @param context
065: * @return an AtomicValue, a value of the required type; or an ErrorValue
066: */
067:
068: public AtomicValue convertPrimitive(BuiltInAtomicType requiredType,
069: boolean validate, XPathContext context) {
070: switch (requiredType.getPrimitiveType()) {
071: case Type.G_YEAR:
072: case Type.ANY_ATOMIC:
073: case Type.ITEM:
074: return this ;
075:
076: case Type.STRING:
077: return new StringValue(getStringValueCS());
078: case Type.UNTYPED_ATOMIC:
079: return new UntypedAtomicValue(getStringValueCS());
080: default:
081: ValidationException err = new ValidationException(
082: "Cannot convert gYear to "
083: + requiredType.getDisplayName());
084: err.setErrorCode("XPTY0004");
085: err.setIsTypeError(true);
086: return new ValidationErrorValue(err);
087: }
088: }
089:
090: public CharSequence getStringValueCS() {
091:
092: FastStringBuffer sb = new FastStringBuffer(16);
093: int yr = year;
094: if (year < 0) {
095: sb.append('-');
096: yr = -yr + 1; // no year zero in lexical space
097: }
098: appendString(sb, yr, (yr > 9999 ? (yr + "").length() : 4));
099:
100: if (hasTimezone()) {
101: appendTimezone(sb);
102: }
103:
104: return sb;
105:
106: }
107: }
108:
109: //
110: // The contents of this file are subject to the Mozilla Public License Version 1.0 (the "License");
111: // you may not use this file except in compliance with the License. You may obtain a copy of the
112: // License at http://www.mozilla.org/MPL/
113: //
114: // Software distributed under the License is distributed on an "AS IS" basis,
115: // WITHOUT WARRANTY OF ANY KIND, either express or implied.
116: // See the License for the specific language governing rights and limitations under the License.
117: //
118: // The Original Code is: all this file.
119: //
120: // The Initial Developer of the Original Code is Saxonica Limited
121: //
122: // Portions created by (your name) are Copyright (C) (your legal entity). All Rights Reserved.
123: //
124: // Contributor(s): none
125: //
|