001/* 002 * ModeShape (http://www.modeshape.org) 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016package org.modeshape.schematic.internal.document; 017 018import java.util.Collection; 019import java.util.Iterator; 020import java.util.Set; 021 022/** 023 * An {@link IndexSequence} is a lightweight ordered sequence of string representing array indexes. It is lightweight because it 024 * shares and reuses the strings for indexes less than the {@link #MAXIMUM_KEY_COUNT maximum key count}. 025 * 026 * @author Randall Hauch <rhauch@redhat.com> (C) 2011 Red Hat Inc. 027 */ 028public class IndexSequence implements Set<String> { 029 protected static final String[] EMPTY_ARRAY = new String[0]; 030 protected static final String[] INDEX_VALUES; 031 protected static final int MAXIMUM_KEY_COUNT = 250; 032 static { 033 String[] values = new String[MAXIMUM_KEY_COUNT]; 034 for (int i = 0; i != MAXIMUM_KEY_COUNT; ++i) { 035 values[i] = Integer.toString(i); 036 } 037 INDEX_VALUES = values; 038 } 039 040 /** 041 * Obtain an iterator for the indexes up to the specified size. 042 * 043 * @param size the number of indexes 044 * @return the iterator of string indexes; never null 045 */ 046 public static Iterator<String> indexesTo( int size ) { 047 return new IndexSequence(size).iterator(); 048 } 049 050 /** 051 * Obtain an iterator for the indexes up the {@link Integer#MAX_VALUE largest} integer. This is efficient, because it only 052 * builds strings as needed. 053 * 054 * @return the iterator of string indexes; never null 055 */ 056 public static Iterator<String> infiniteSequence() { 057 return new IndexSequence(Integer.MAX_VALUE).iterator(); 058 } 059 060 protected final int size; 061 062 public IndexSequence( int size ) { 063 this.size = size; 064 } 065 066 @Override 067 public boolean add( String e ) { 068 throw new UnsupportedOperationException(); 069 } 070 071 @Override 072 public boolean addAll( Collection<? extends String> c ) { 073 throw new UnsupportedOperationException(); 074 } 075 076 @Override 077 public void clear() { 078 throw new UnsupportedOperationException(); 079 } 080 081 @Override 082 public boolean contains( Object o ) { 083 int index = Integer.parseInt(String.valueOf(o)); 084 return index >= 0 && index < size; 085 } 086 087 @Override 088 public boolean containsAll( Collection<?> c ) { 089 for (Object value : c) { 090 if (!contains(value)) return false; 091 } 092 return true; 093 } 094 095 @Override 096 public boolean isEmpty() { 097 return size == 0; 098 } 099 100 @Override 101 public Iterator<String> iterator() { 102 return new Iterator<String>() { 103 private int index = 0; 104 105 @Override 106 public boolean hasNext() { 107 return index < size; 108 } 109 110 @Override 111 public String next() { 112 return index < MAXIMUM_KEY_COUNT ? INDEX_VALUES[index++] : String.valueOf(index++); 113 } 114 115 @Override 116 public void remove() { 117 throw new UnsupportedOperationException(); 118 } 119 }; 120 } 121 122 @Override 123 public boolean remove( Object o ) { 124 throw new UnsupportedOperationException(); 125 } 126 127 @Override 128 public boolean removeAll( Collection<?> c ) { 129 throw new UnsupportedOperationException(); 130 } 131 132 @Override 133 public boolean retainAll( Collection<?> c ) { 134 throw new UnsupportedOperationException(); 135 } 136 137 @Override 138 public int size() { 139 return size; 140 } 141 142 @Override 143 public Object[] toArray() { 144 if (size == 0) return EMPTY_ARRAY; 145 String[] copy = new String[size]; 146 System.arraycopy(INDEX_VALUES, 0, copy, 0, size); 147 return copy; 148 } 149 150 @Override 151 public <T> T[] toArray( T[] a ) { 152 throw new UnsupportedOperationException(); 153 } 154}