arrayvalue.java
来自「RESIN 3.2 最新源码」· Java 代码 · 共 1,663 行 · 第 1/3 页
JAVA
1,663 行
/* * Copyright (c) 1998-2008 Caucho Technology -- all rights reserved * * This file is part of Resin(R) Open Source * * Each copy or derived work must preserve the copyright notice and this * notice unmodified. * * Resin Open Source is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * Resin Open Source is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE, or any warranty * of NON-INFRINGEMENT. See the GNU General Public License for more * details. * * You should have received a copy of the GNU General Public License * along with Resin Open Source; if not, write to the * * Free Software Foundation, Inc. * 59 Temple Place, Suite 330 * Boston, MA 02111-1307 USA * * @author Scott Ferguson */package com.caucho.quercus.env;import com.caucho.quercus.Location;import com.caucho.quercus.function.Marshal;import com.caucho.quercus.function.MarshalFactory;import com.caucho.vfs.WriteStream;import java.io.IOException;import java.io.Serializable;import java.lang.reflect.Array;import java.util.*;import java.util.logging.Level;import java.util.logging.Logger;/** * Represents a PHP array value. */abstract public class ArrayValue extends Value { private static final Logger log = Logger.getLogger(ArrayValue.class.getName()); protected static final StringValue KEY = new StringBuilderValue("key"); protected static final StringValue VALUE = new StringBuilderValue("value"); public static final GetKey GET_KEY = new GetKey(); public static final GetValue GET_VALUE = new GetValue(); protected Entry _current; protected ArrayValue() { } /** * Returns the type. */ @Override public String getType() { return "array"; } /** * Returns the ValueType. */ @Override public ValueType getValueType() { return ValueType.ARRAY; } /** * Converts to a boolean. */ @Override public boolean toBoolean() { return getSize() != 0; } /** * Converts to a string. */ @Override public String toString() { return "Array"; } /** * Converts to an object. */ public Object toObject() { return null; } /** * Converts to a java object. */ @Override public Object toJavaObject() { return this; } // // Conversions // /** * Converts to an object. */ @Override public Value toArray() { return this; } /** * Converts to an array value */ @Override public ArrayValue toArrayValue(Env env) { return this; } /** * Converts to an object. */ @Override public Value toObject(Env env) { Value obj = env.createObject(); for (Entry entry = getHead(); entry != null; entry = entry._next) { Value key = entry.getKey(); if (key instanceof StringValue) { // XXX: intern? obj.putField(env, key.toString(), entry.getValue()); } } return obj; } /** * Converts to a java List object. */ @Override public Collection toJavaCollection(Env env, Class type) { Collection coll = null; if (type.isAssignableFrom(HashSet.class)) { coll = new HashSet(); } else if (type.isAssignableFrom(TreeSet.class)) { coll = new TreeSet(); } else { try { coll = (Collection) type.newInstance(); } catch (Throwable e) { log.log(Level.FINE, e.toString(), e); env.warning(L.l("Can't assign array to {0}", type.getName())); return null; } } for (Entry entry = getHead(); entry != null; entry = entry._next) { coll.add(entry.getValue().toJavaObject()); } return coll; } /** * Converts to a java List object. */ @Override public List toJavaList(Env env, Class type) { List list = null; if (type.isAssignableFrom(ArrayList.class)) { list = new ArrayList(); } else if (type.isAssignableFrom(LinkedList.class)) { list = new LinkedList(); } else if (type.isAssignableFrom(Vector.class)) { list = new Vector(); } else { try { list = (List) type.newInstance(); } catch (Throwable e) { log.log(Level.FINE, e.toString(), e); env.warning(L.l("Can't assign array to {0}", type.getName())); return null; } } for (Entry entry = getHead(); entry != null; entry = entry._next) { list.add(entry.getValue().toJavaObject()); } return list; } /** * Converts to a java object. */ @Override public Map toJavaMap(Env env, Class type) { Map map = null; if (type.isAssignableFrom(TreeMap.class)) { map = new TreeMap(); } else if (type.isAssignableFrom(LinkedHashMap.class)) { map = new LinkedHashMap(); } else { try { map = (Map) type.newInstance(); } catch (Throwable e) { log.log(Level.FINE, e.toString(), e); env.warning(L.l("Can't assign array to {0}", type.getName())); return null; } } for (Entry entry = getHead(); entry != null; entry = entry._next) { map.put(entry.getKey().toJavaObject(), entry.getValue().toJavaObject()); } return map; } /** * Returns true for an array. */ @Override public boolean isArray() { return true; } /** * Copy as a return value */ @Override public Value copyReturn() { return copy(); // php/3a5e } /** * Copy for assignment. */ @Override abstract public Value copy(); /** * Copy for serialization */ @Override abstract public Value copy(Env env, IdentityHashMap<Value,Value> map); /** * Returns the size. */ @Override abstract public int getSize(); /** * Returns the count(). */ @Override public int getCount(Env env) { return getSize(); } /** * Returns the count(). */ @Override public int getCountRecursive(Env env) { env.stub("recursive count of array unimplemented"); return getSize(); } /** * Returns true if the value is empty */ @Override public boolean isEmpty() { return getSize() == 0; } /** * Clears the array */ abstract public void clear(); @Override public int cmp(Value rValue) { return cmpImpl(rValue, 1); } private int cmpImpl(Value rValue, int resultIfKeyMissing) { // "if key from operand 1 is not found in operand 2 then // arrays are uncomparable, otherwise - compare value by value" // php/335h if (!rValue.isArray()) return 1; int lSize = getSize(); int rSize = rValue.toArray().getSize(); if (lSize != rSize) return lSize < rSize ? -1 : 1; for (Map.Entry<Value,Value> entry : entrySet()) { Value lElementValue = entry.getValue(); Value rElementValue = rValue.get(entry.getKey()); if (!rElementValue.isset()) return resultIfKeyMissing; int cmp = lElementValue.cmp(rElementValue); if (cmp != 0) return cmp; } return 0; } /** * Returns true for less than */ @Override public boolean lt(Value rValue) { // php/335h return cmpImpl(rValue, 1) < 0; } /** * Returns true for less than or equal to */ @Override public boolean leq(Value rValue) { // php/335h return cmpImpl(rValue, 1) <= 0; } /** * Returns true for greater than */ @Override public boolean gt(Value rValue) { // php/335h return cmpImpl(rValue, -1) > 0; } /** * Returns true for greater than or equal to */ @Override public boolean geq(Value rValue) { // php/335h return cmpImpl(rValue, -1) >= 0; } /** * Adds a new value. */ @Override abstract public Value put(Value key, Value value); /** * Add */ @Override abstract public Value put(Value value); /** * Add to front. */ abstract public ArrayValue unshift(Value value); /** * Splices. */ abstract public ArrayValue splice(int begin, int end, ArrayValue replace); /** * Returns the value as an array. */ @Override public Value getArray(Value index) { Value value = get(index); Value array = value.toAutoArray(); if (value != array) { value = array; put(index, value); } return value; } /** * Returns the value as an argument which may be a reference. */ @Override abstract public Value getArg(Value index); /** * Returns the field value, creating an object if it's unset. */ @Override public Value getObject(Env env, Value fieldName) { Value value = get(fieldName); Value object = value.toAutoObject(env); if (value != object) { value = object; put(fieldName, value); } return value; } /** * Sets the array ref. */ @Override abstract public Value putRef(); /** * Creatse a tail index. */ abstract public Value createTailKey(); /** * Returns a union of this array and the rValue as array. * If the rValue is not an array, the returned union contains the elements * of this array only. * * To append a value to this ArrayValue use the {@link #put(Value)} method. */ @Override public Value add(Value rValue) { rValue = rValue.toValue(); if (! (rValue instanceof ArrayValue)) return copy(); ArrayValue rArray = (ArrayValue) rValue; ArrayValue result = new ArrayValueImpl(rArray); for (Entry entry = getHead(); entry != null; entry = entry._next) { result.put(entry.getKey(), entry.getValue()); } return result; } @Override public Iterator<Map.Entry<Value, Value>> getIterator(Env env) { return new EntryIterator(getHead()); } @Override public Iterator<Value> getKeyIterator(Env env) { return new KeyIterator(getHead()); } @Override public Iterator<Value> getValueIterator(Env env) { return new ValueIterator(getHead()); } /** * Gets a new value. */ @Override abstract public Value get(Value key); /** * Returns the value in the array as-is. * (i.e. without calling toValue() on it). */ public Value getRaw(Value key) { return get(key); } /** * Removes a value. */ @Override abstract public Value remove(Value key); /** * Returns the array ref. */ @Override
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?