001/* 002 * Copyright (c) 2009 The openGion Project. 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, 013 * either express or implied. See the License for the specific language 014 * governing permissions and limitations under the License. 015 */ 016package org.opengion.fukurou.util; 017 018import java.util.LinkedHashSet; 019import java.util.Collection; // 7.0.1.1 (2018/10/22) 020import java.util.Collections; 021import java.util.Iterator; 022import java.util.function.BiConsumer; 023 024import static org.opengion.fukurou.system.HybsConst.BUFFER_MIDDLE; // 7.0.1.1 (2018/10/22) 025 026/** 027 * ArraySet.java は、LinkedHashSet を継承した、Setオブジェクトです。 028 * 029 * 初期オブジェクト作成のための、引数に、配列(可変長配列)を渡せるようにしています。 030 * また、Iterable#forEach( Consumer ) で、ループカウンタが使えるように、新しく、 031 * BiConsumer を引数に取る forEach( int , BiConsumer ) メソッドを用意しています。 032 * 033 * @og.rev 6.4.3.4 (2016/03/11) 新規追加 034 * 035 * @version 6.4 036 * @author Kazuhiko Hasegawa 037 * @since JDK8.0, 038 */ 039public class ArraySet<E> extends LinkedHashSet<E> { 040 /** このプログラムのVERSION文字列を設定します。 {@value} */ 041 private static final String VERSION = "7.0.1.1 (2018/10/22)" ; 042 private static final long serialVersionUID = 701120181022L ; 043 044 /** 045 * LinkedHashSet を継承した、Setオブジェクトです。 046 * 047 * 初期オブジェクト作成のための、引数に、配列を渡せるようにしています。 048 * 049 * @og.rev 7.0.1.1 (2018/10/22) 新規追加 050 * 051 * @param elements 初期値として設定する可変長配列 052 */ 053 @SuppressWarnings({"unchecked", "varargs"}) 054 public ArraySet( final E... elements ) { 055 super(); 056 Collections.addAll( this, elements ); 057 } 058 059 /** 060 * 他のCollectionオブジェクトを追加します。 061 * 062 * @og.rev 6.4.3.4 (2016/03/11) 新規追加 063 * 064 * @param collect Collectionオブジェクトの可変長配列 065 * @return 自分自身 066 */ 067 @SuppressWarnings({"unchecked"}) 068 public ArraySet<E> addAll( final Collection<E>... collect ) { 069 if( collect != null && collect.length > 0 ) { 070 for( final Collection<E> obj : collect ) { 071 super.addAll( obj ); 072 } 073 } 074 return this ; 075 } 076 077 /** 078 * Iterable#forEach( Consumer ) で、引数に、ループカウンタを使用できるメソッドです。 079 * 080 * ラムダ式から参照されるローカル変数は、finalまたは事実上のfinalである必要があります。 081 * ところが、訳あって、ループカウンタが必要です。そこで、内部処理として、ループカウンタを 082 * 用意しておき、それを、ラムダ式の引数として渡す方法で、対応します。 083 * 一覧の処理は、内部で、Iterator#hasNext() と、Iterator#next() を使用しているため、 084 * インスタンスレベルのsynchronized ブロックを使用しています。 085 * 086 * @og.rev 6.4.3.4 (2016/03/11) 新規追加 087 * 088 * @param cnt カウンタの初期値 089 * @param action 各要素に対して実行されるアクション( カウンタ、内部オブジェクト ) 090 * @see Iterable#forEach( Consumer ) 091 */ 092 public void forEach( final int cnt , final BiConsumer<Integer ,E> action ) { 093 int i = cnt; 094 095 synchronized( this ) { 096 final Iterator<E> ite = iterator(); 097 while( ite.hasNext() ) { 098 action.accept( i++ , ite.next() ); 099 } 100 } 101 } 102 103 /** 104 * このオブジェクトの内部表現を、文字列にして返します。 105 * 内部オブジェクトの toString() を順番に呼んで、カンマで連結した文字列を返します。 106 * 107 * @og.rev 7.0.1.1 (2018/10/22) 新規追加 108 * 109 * @return 引数に対する値 110 * @og.rtnNotNull 111 */ 112 @Override 113 public String toString() { 114 final StringBuilder buf = new StringBuilder( BUFFER_MIDDLE ); 115 116 synchronized( this ) { 117 final Iterator<E> ite = iterator(); 118 while( ite.hasNext() ) { 119 buf.append( ite.next() ).append( ',' ); 120 } 121 } 122 123 if( buf.length() > 0 ) { buf.setLength( buf.length()-1 ); } // 最後のカンマを削除 124 125 return buf.toString(); 126 } 127}