package com.taobao.tddl.executor.record; import java.util.ArrayList; import java.util.Arrays; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.Map.Entry; import com.taobao.tddl.common.utils.logger.Logger; import com.taobao.tddl.common.utils.logger.LoggerFactory; import com.taobao.tddl.executor.common.IRecord; import com.taobao.tddl.optimizer.config.table.ColumnMeta; import com.taobao.tddl.optimizer.core.datatype.DataType; /** * @author mengshi.sunmengshi 2013-12-3 下午1:51:05 * @since 5.0.0 */ public class FixedLengthRecord extends CloneableRecord { private final static Logger logger = LoggerFactory.getLogger(FixedLengthRecord.class); protected Object[] values; protected Map<String, Integer> index; public FixedLengthRecord(Map<String, Integer> index, int mapSizeCache){ this.index = index; this.values = new Object[index.size()]; } public FixedLengthRecord(List<ColumnMeta> keys){ this.index = new HashMap(keys.size()); for (ColumnMeta key : keys) { if (!index.containsKey(key.getName())) { index.put(key.getName(), index.size()); } } this.values = new Object[index.size()]; } @Override public Object get(String name, String key) { return getIngoreTableName(key); } @Override public Object getIngoreTableName(String key) { return get(key); } @Override public Object getIngoreTableNameUpperCased(String key) { return get(key); } @Override public CloneableRecord put(String name, String key, Object value) { put(key, value); return this; } @Override public IRecord put(String key, Object value) { Integer indexNum = index.get(key); if (indexNum == null) { throw new IllegalArgumentException("can't find key :" + key + " . current indexes is " + index); } values[indexNum] = value; return this; } @Override public Object get(String key) { Integer i = index.get(key); if (i == null) { if (logger.isDebugEnabled()) { logger.debug("can't find key :" + key + " .index list : " + index); } return null; } return values[i]; } @Override public IRecord putAll(Map<String, Object> all) { for (Entry<String, Object> e : all.entrySet()) { put(e.getKey(), e.getValue()); } return this; } @Override public Object getValueByIndex(int index) { return values[index]; } @Override public IRecord setValueByIndex(int index, Object val) { values[index] = val; return this; } @Override public IRecord addAll(List<Object> values) { values.addAll(values); return this; } @Override public Map<String, Integer> getColumnMap() { return index; } @Override public List<String> getColumnList() { List<String> ret = new ArrayList(index.size()); ret.addAll(index.keySet()); return ret; } @Override public List<Object> getValueList() { return Arrays.asList(values); } @Override public Map<String, Object> getMap() { Map<String, Object> ret = new HashMap(values.length); for (Entry<String, Integer> e : index.entrySet()) { ret.put(e.getKey(), values[e.getValue()]); } return ret; } @SuppressWarnings({ "unchecked", "rawtypes" }) @Override public int compareTo(IRecord o) { List<Object> values1 = null; if (o instanceof NamedRecord) { values1 = ((FixedLengthRecord) ((NamedRecord) o).getRecord()).getValueList(); } else { values1 = ((FixedLengthRecord) o).getValueList(); } for (int k = 0; k < values1.size(); k++) { Object v1 = values1.get(k); Object v = values[k]; int r = 0; if (v instanceof byte[]) { byte[] a = (byte[]) v; byte[] b = (byte[]) v1; int len = Math.min(a.length, b.length); for (int i = 0; i < len; i++) { byte ai = a[i]; byte bi = b[i]; if (ai != bi) { if (ai - bi != 0) { r = ai - bi; break; } } } r = a.length - b.length; } else { if (v != null && v1 != null) { r = ((Comparable) v).compareTo(v1); } else if (v == null && v1 == null) { r = 0; } else if (v == null) { r = -1; } else if (v1 == null) { r = 1; } } if (r != 0) { return r; } } return 0; } @Override public Object clone() { FixedLengthRecord fixedLengthRecord = (FixedLengthRecord) super.clone(); if (fixedLengthRecord.values != null) { fixedLengthRecord.values = Arrays.copyOf(fixedLengthRecord.values, fixedLengthRecord.values.length); } return fixedLengthRecord; } @Override public String toString() { return "FixedLengthRecord{" + " values=" + Arrays.asList(values) + ", index=" + index + '}'; } @Override public boolean equals(Object obj) { if (obj == null) { return false; } // if (getClass() != obj.getClass()) { // return false; // } final FixedLengthRecord other; if (obj instanceof FixedLengthRecord) { other = (FixedLengthRecord) obj; } else if (obj instanceof NamedRecord) { NamedRecord nr = (NamedRecord) obj; if (nr.record != null && nr.record instanceof FixedLengthRecord) { other = (FixedLengthRecord) nr.record; } else { return false; } } else { return false; } if (!Arrays.deepEquals(this.values, other.values)) { return false; } if (this.index != other.index && (this.index == null || !this.index.equals(other.index))) { return false; } return true; } @Override public int hashCode() { int hash = 7; hash = 29 * hash + Arrays.deepHashCode(this.values); hash = 29 * hash + (this.index != null ? this.index.hashCode() : 0); return hash; } @Override public DataType getType(int index) { // TODO Auto-generated method stub return null; } @Override public DataType getType(String columnName) { // TODO Auto-generated method stub return null; } }