(리터럴 방식으로) HashMap을 직접 초기화하려면 어떻게 해야 합니까?
Java HashMap을 다음과 같이 초기화하는 방법이 있습니까?
Map<String,String> test =
new HashMap<String, String>{"test":"test","test":"test"};
올바른 구문은 무엇입니까?저는 이것에 대해 아무것도 발견하지 못했습니다.이게 가능합니까?맵을 작성할 때 변경되지 않고 미리 알려진 "최종/정적" 값을 맵에 넣을 수 있는 가장 짧은/빠른 방법을 찾고 있습니다.
모든 버전
개개개개 1 있 : 。Collections.singletonMap("key", "value")
.
Java 버전9 이후의 경우:
네, 이제 가능합니다.Java 9에서는 맵 작성을 단순화하는 공장 방식이 몇 가지 추가되었습니다.
// this works for up to 10 elements:
Map<String, String> test1 = Map.of(
"a", "b",
"c", "d"
);
// this works for any number of elements:
import static java.util.Map.entry;
Map<String, String> test2 = Map.ofEntries(
entry("a", "b"),
entry("c", "d")
);
에서는 둘 다에 대해 하겠습니다.test
★★★★★★★★★★★★★★★★★」test2
지도를 표현하는 방식이 다를 뿐이지 똑같을 겁니다.Map.of
맵 되며 method는 "10"으로 됩니다.Map.ofEntries
메서드에는 이러한 제한이 없습니다.
이 경우 결과 맵은 불변의 맵이 됩니다.수 예를 맵을 할 수 .mutableMap = new HashMap<>(Map.of("a", "b"));
Java 버전8까지:
아니요, 모든 요소를 수동으로 추가해야 합니다.어나니머스 서브클래스에서 이니셜라이저를 사용하여 구문을 조금 짧게 만들 수 있습니다.
Map<String, String> myMap = new HashMap<String, String>() {{
put("a", "b");
put("c", "d");
}};
그러나 경우에 따라서는 익명 서브클래스에 의해 불필요한 동작이 발생할 수 있습니다.예를 들어 다음과 같습니다.
- 추가 클래스를 생성하여 메모리 소비량, 디스크 공간 소비량 및 부팅 시간을 증가시킵니다.
- 비정적 방식의 경우:작성 메서드가 호출된 개체에 대한 참조가 있습니다.즉, 외부 클래스의 오브젝트는 생성된 맵오브젝트가 아직 참조되고 있는 동안에는 가비지를 수집할 수 없기 때문에 추가 메모리가 차단됩니다.
초기화 기능을 사용하면 이니셜라이저에서 맵을 생성할 수도 있지만 다음과 같은 부작용을 피할 수 있습니다.
Map<String, String> myMap = createMap();
private static Map<String, String> createMap() {
Map<String,String> myMap = new HashMap<String,String>();
myMap.put("a", "b");
myMap.put("c", "d");
return myMap;
}
이게 한 가지 방법이에요.
Map<String, String> h = new HashMap<String, String>() {{
put("a","b");
}};
단, 주의하여 위의 코드를 이해해 주십시오(해시맵에서 상속되는 새 클래스가 생성됩니다).따라서 자세한 내용은 http://www.c2.com/cgi/wiki?DoubleBraceInitialization 또는 Guava를 참조하십시오.
Map<String, Integer> left = ImmutableMap.of("a", 1, "b", 2, "c", 3);
ImmutableMap.of
는 최대 5개의 엔트리로 동작합니다.그렇지 않으면 builder: source를 사용합니다.
서드파티 libs를 허용하면 Guava의 UnmutableMap을 사용하여 문자 그대로의 간결함을 실현할 수 있습니다.
Map<String, String> test = ImmutableMap.of("k1", "v1", "k2", "v2");
이는 최대 5개의 키/값 쌍에 대해 작동하며, 그렇지 않으면 빌더를 사용할 수 있습니다.
Map<String, String> test = ImmutableMap.<String, String>builder()
.put("k1", "v1")
.put("k2", "v2")
...
.build();
- Guava의 UnmutableMap 구현은 Java의 HashMap 구현과 다르다는 점에 유의하십시오(가장 주목할 점은 불변하며 늘 키/값을 허용하지 않습니다).
- 자세한 내용은 Guava의 불변의 컬렉션 유형에 대한 사용자 가이드 문서를 참조하십시오.
이를 위한 직접적인 방법은 없습니다 - Java에는 지도 리터럴이 없습니다(아직 Java 8용으로 제안되었다고 생각합니다).
다음과 같은 사람도 있습니다.
Map<String,String> test = new HashMap<String, String>(){{
put("test","test"); put("test","test");}};
그러면 HashMap의 어나니머스 서브클래스가 생성됩니다.이 서브클래스의 인스턴스 이니셜라이저는 이러한 값을 저장합니다.(그런데 지도는 같은 값의 2배를 포함할 수 없습니다.두 번째 입력은 첫 번째 값을 덮어씁니다.다음 예에서는 다른 값을 사용합니다.)
통상적인 방법은 (로컬 변수의 경우) 다음과 같습니다.
Map<String,String> test = new HashMap<String, String>();
test.put("test","test");
test.put("test1","test2");
의 '' ''가test
또는 인스턴스에 넣습니다.map은 instance 변수입니다.컨스트럭터 또는 인스턴스 이니셜라이저에 초기화를 넣습니다.
Map<String,String> test = new HashMap<String, String>();
{
test.put("test","test");
test.put("test1","test2");
}
의 '' ''가test
.map map 、 map 、 map map map 。초기화를 스태틱인테셜라이저에 넣습니다.
static Map<String,String> test = new HashMap<String, String>();
static {
test.put("test","test");
test.put("test1","test2");
}
초기화 후 .Collections.unmodifiableMap(...)
스태틱 이니셜라이저에서도 이 작업을 수행할 수 있습니다.
static Map<String,String> test;
{
Map<String,String> temp = new HashMap<String, String>();
temp.put("test","test");
temp.put("test1","test2");
test = Collections.unmodifiableMap(temp);
}
수 test
시험해보고 여기에 보고하세요.)
Map<String,String> test = new HashMap<String, String>()
{
{
put(key1, value1);
put(key2, value2);
}
};
7 .Java 7 varargs는 varargs를 만듭니다.HashMapBuilder
public static HashMap<String, String> build(String... data){
HashMap<String, String> result = new HashMap<String, String>();
if(data.length % 2 != 0)
throw new IllegalArgumentException("Odd number of arguments");
String key = null;
Integer step = -1;
for(String value : data){
step++;
switch(step % 2){
case 0:
if(value == null)
throw new IllegalArgumentException("Null key value");
key = value;
continue;
case 1:
result.put(key, value);
break;
}
}
return result;
}
다음과 같은 방법을 사용합니다.
HashMap<String,String> data = HashMapBuilder.build("key1","value1","key2","value2");
자바 8
에서는 8을 사용할 .Streams/Collectors
일을 할 수 있도록 말이야.
Map<String, String> myMap = Stream.of(
new SimpleEntry<>("key1", "value1"),
new SimpleEntry<>("key2", "value2"),
new SimpleEntry<>("key3", "value3"))
.collect(toMap(SimpleEntry::getKey, SimpleEntry::getValue));
이 방법에는 Anonymous 클래스를 만들지 않는다는 장점이 있습니다.
Import는 다음과 같습니다.
import static java.util.stream.Collectors.toMap;
import java.util.AbstractMap.SimpleEntry;
물론 다른 답변에서도 언급했듯이 Java 9 이후에서는 동일한 작업을 보다 쉽게 수행할 수 있습니다.
dr;dr
Map.of…
Java 9 の java java java java 。
Map< String , String > animalSounds =
Map.of(
"dog" , "bark" , // key , value
"cat" , "meow" , // key , value
"bird" , "chirp" // key , value
)
;
Map.of
Java 9는 사용자가 원하는 작업을 수행하기 위한 일련의 정적 메서드를 추가했습니다.리터럴 구문을 사용하여 불변의 인스턴스를 만듭니다.
맵(엔트리의 집합)은 불변하기 때문에 인스턴스화 후 엔트리를 추가하거나 삭제할 수 없습니다.또한 각 엔트리의 키와 값은 변경할 수 없습니다.NULL이 허용되지 않거나 중복 키가 허용되지 않으며 매핑 반복 순서가 임의인 등 다른 규칙에 대해서는 Javadoc을 참조하십시오.
이 방법들에 대해 알아보겠습니다.그날 작업하는 사람에게의 요일 맵의 샘플 데이터를 사용합니다.
Person alice = new Person( "Alice" );
Person bob = new Person( "Bob" );
Person carol = new Person( "Carol" );
Map.of()
Map.of
빈칸을 만듭니다.Map
수 엔트리를 할 수 . 수정할 수 없으므로 엔트리를 추가할 수 없습니다.다음으로 엔트리가 없는 빈 맵의 예를 나타냅니다.
Map < DayOfWeek, Person > dailyWorkerEmpty = Map.of();
dailyWorkerEmpty.toString(): {}
Map.of( … )
Map.of( k , v , k , v , …)
는 1 ~ 10개의 키와 값의 페어를 필요로 하는 몇 가지 방법입니다.다음으로 2개의 엔트리의 예를 나타냅니다.
Map < DayOfWeek, Person > weekendWorker =
Map.of(
DayOfWeek.SATURDAY , alice , // key , value
DayOfWeek.SUNDAY , bob // key , value
)
;
weekendWorker.toString(): {SUNDAY=Person{name='Bob'}, 토요일=Person{name='앨리스 }}
Map.ofEntries( … )
Map.ofEntries( Map.Entry , … )
는, 인터페이스를 실장하고 있는 임의의 수의 오브젝트를 취득합니다.Java는 해당 인터페이스를 구현하는2개의 클래스를 번들합니다.하나는 가변 클래스이고 다른 하나는 불변 클래스입니다.다만, 구체적인 클래스를 지정할 필요는 없습니다.메서드를 호출하고 키와 값을 전달하면 구현 인터페이스의 클래스 객체를 얻을 수 있습니다.
Map < DayOfWeek, Person > weekdayWorker = Map.ofEntries(
Map.entry( DayOfWeek.MONDAY , alice ) , // Call to `Map.entry` method returns an object implementing `Map.Entry`.
Map.entry( DayOfWeek.TUESDAY , bob ) ,
Map.entry( DayOfWeek.WEDNESDAY , bob ) ,
Map.entry( DayOfWeek.THURSDAY , carol ) ,
Map.entry( DayOfWeek.FRIDAY , carol )
);
weekdayWorker.toString(): {WEDNSDAY=Person{name='Bob'}, 화요일=Person{이름='Bob'}, 목요일=Person{이름='Carol'}, 금요일=PRIDAY=Person{이름='}, 월요일={이름='CAROL'}앨리스 }}
Map.copyOf
Java 10이 메서드를 추가했습니다. 기존 맵을 전달하고 해당 맵의 불변의 복사본을 가져옵니다.
메모들
를 통해 입니다.Map.of
는 보증되지 않습니다.엔트리의 순서는 임의입니다.문서에서는 주문이 변경될 수 있다고 경고하고 있으므로 표시된 주문에 따라 코드를 작성하지 마십시오.
은, 「」의 「」에 해 주세요.Map.of…
메서드는 지정되지 않은 클래스의 를 반환합니다.기본 콘크리트 클래스는 Java 버전에 따라 다를 수도 있습니다.이러한 익명성을 통해 Java는 특정 데이터에 가장 적합한 다양한 구현 중에서 선택할 수 있습니다.예를 들어, 키가 열거형일 경우 Java는 커버 아래에 를 사용할 수 있습니다.
해시맵은 다음 방법으로 초기화할 수 있습니다.
생성자를 사용한 해시 맵
맵 <String, String> hashMap = 새로운 HashMap <String, String> ( ) ;
hashMap.put("hcl", "amit"); hashMap.put("tcs","ravi");
해시맵에는 4가지 타입의 컨스트럭터가 있기 때문에 요건에 따라 초기화할 수 있습니다.현재 HashMap(int initialCapacity) 생성자를 사용하고 있습니다.
Map<String, String> hashMap = new HashMap<String, String>(3);
hashMap.put("virat", "cricket");
hashMap.put("amit","football");
컬렉션을 사용한 싱글톤 해시 맵
Map<String, String> immutableMap = Collections.singletonMap("rohit", "cricket");
컬렉션을 사용한 빈 해시 맵
Map<String, String> emptyMap = Collections.emptyMap();
해시맵을 만드는 익명 서브클래스
Map<String, String> map = new HashMap<String, String>() {{ put("hcl", "amit"); put("tcs","ravi"); put("wipro","anmol"); }};
Johnny Willer의 답변에 대해 간략하게 경고하고 싶습니다.
Collectors.toMap
Map.merge
null 값을 예상하지 않기 때문에 null 값이 느려집니다.NullPointerException
다음 버그리포트에서 설명한 바와 같이 https://bugs.openjdk.java.net/browse/JDK-8148463
번 default, 가, 폴, 폴, 폴, 폴, 폴, 폴, 폴, 폴, 폴, 폴, 폴, also, also, also.Collectors.toMap
IllegalStateException
.
Java 8에서 빌더 구문을 사용하여 늘 값을 가진 맵을 얻는 다른 방법은 해시맵에 의해 지원되는 커스텀컬렉터를 쓰는 것입니다(늘 값을 사용할 수 있기 때문입니다).
Map<String, String> myMap = Stream.of(
new SimpleEntry<>("key1", "value1"),
new SimpleEntry<>("key2", (String) null),
new SimpleEntry<>("key3", "value3"),
new SimpleEntry<>("key1", "value1updated"))
.collect(HashMap::new,
(map, entry) -> map.put(entry.getKey(),
entry.getValue()),
HashMap::putAll);
SimpleEntry를 가진 AbstractMap 클래스를 사용하여 불변의 맵을 생성할 수 있습니다.
Map<String, String> map5 = Stream.of(
new AbstractMap.SimpleEntry<>("Sakshi","java"),
new AbstractMap.SimpleEntry<>("fine","python")
).collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));
System.out.println(map5.get("Sakshi"));
map5.put("Shiva", "Javascript");
System.out.println(map5.get("Shiva"));// here we can add multiple entries.
간단한 유틸리티 클래스를 사용하여 맵을 유창한 방법으로 초기화합니다.
Map<String, String> map = MapInit
.init("key1", "value1")
.put("key2", "value2")
.put("key3", "value3")
.getMap();
유틸리티 클래스는 키와 값의 종류, 엔트리의 수, 맵의 종류 등 제한되지 않습니다.
유틸리티 클래스는 다음과 같습니다.
public class MapInit<K, V, T extends Map<K, V>> {
private final T map;
private MapInit(final T map) {
this.map = map;
}
public T getMap() {
return this.map;
}
public static <K, V> MapInit<K, V, HashMap<K, V>> init(final K key, final V value) {
return init(HashMap::new, key, value);
}
public static <K, V, T extends Map<K, V>> MapInit<K, V, T> init(final Supplier<T> mapSupplier, final K key, final V value) {
return new MapInit<>(mapSupplier.get()) //
.put(key, value);
}
public MapInit<K, V, T> put(final K key, final V value) {
this.map.put(key, value);
return this;
}
}
될 것 요.Map.of
) 는 2가지 간단한 사용할 수 있습니다(Java 9).
설정된 파라미터 양으로 작성
예
public <K,V> Map<K,V> mapOf(K k1, V v1, K k2, V v2 /* perhaps more parameters */) {
return new HashMap<K, V>() {{
put(k1, v1);
put(k2, v2);
// etc...
}};
}
목록을 사용하여 만들기
특정 파라미터 세트에 대해 많은 메서드를 작성하지 않고 목록을 사용하여 작성할 수도 있습니다.
예
public <K, V> Map<K, V> mapOf(List<K> keys, List<V> values) {
if(keys.size() != values.size()) {
throw new IndexOutOfBoundsException("amount of keys and values is not equal");
}
return new HashMap<K, V>() {{
IntStream.range(0, keys.size()).forEach(index -> put(keys.get(index), values.get(index)));
}};
}
참고 이 기능을 사용할 때마다 익명 클래스가 생성되므로 모든 작업에 이 기능을 사용하는 것은 권장되지 않습니다.
키와 값의 쌍을 하나만 배치해야 하는 경우 Collections.singleton Map(키, 값)을 사용할 수 있습니다.
Java 8 이하 사용 시
정적 블록을 사용하여 일부 값을 가진 맵을 초기화할 수 있습니다.예:
public static Map<String,String> test = new HashMap<String, String>
static {
test.put("test","test");
test.put("test1","test");
}
Java 9 이후
Map.of() 메서드를 사용하여 선언 중에 몇 가지 값이 포함된 맵을 초기화할 수 있습니다.예:
public static Map<String,String> test = Map.of("test","test","test1","test");
간단한 방법:
public static Map<String, String> mapWithValues(String...values) {
Map<String, String> map = new HashMap<String, String>();
for (int x = 0; x < values.length; x = x+2) {
map.put(values[x], values[x+1]);
}
return map;
}
됩니다. 초기화 블록을 사용할 수 없는 에는 더더욱 . 특히Map.of()
다른 종류의 지도가 필요하기 때문입니다.
것 같습니다.Supplier
(서양속담, 친구속담)
private final Map<String,Runnable> games = ((Supplier<Map<String,Runnable>>)() -> {
Map<String,Runnable> map = new LinkedHashMap<>();
map.put("solarus",this::playSolarus);
map.put("lichess",this::playLichess);
return map;
}).get();
또는, 독자적인 기능 인터페이스를 작성할 수도 있습니다(제 생각에는 문제 없습니다).
@FunctionalInterface
public interface MapMaker<M> {
static <M extends Map<K,V>,K,V> M make(M map,MapMaker<M> maker) {
maker.build(map);
return map;
}
void build(M map);
}
// Can use LinkedHashMap!
private final Map<String,Runnable> games = MapMaker.make(
new LinkedHashMap<>(),(map) -> {
map.put("solarus",this::playSolarus);
map.put("lichess",this::playLichess);
});
않은 를 사용하는 하지 않습니다.varargs를 사용해야 입니다.Object...
타입의 안전성을 완전히 잃게 됩니다.예를 들어, 예를 들어,Map<String, String>
물론 a는toMap(String... args)
단, 키와 값을 혼동하기 쉽고 홀수 인수는 무효이기 때문에 그다지 예쁘지 않습니다.
다음과 같은 체인 가능한 메서드를 가진 HashMap의 하위 클래스를 만들 수 있습니다.
public class ChainableMap<K, V> extends HashMap<K, V> {
public ChainableMap<K, V> set(K k, V v) {
put(k, v);
return this;
}
}
사용법을 알 수식하다new ChainableMap<String, Object>().set("a", 1).set("b", "foo")
또 다른 접근방식은 공통 빌더 패턴을 사용하는 것입니다.
public class MapBuilder<K, V> {
private Map<K, V> mMap = new HashMap<>();
public MapBuilder<K, V> put(K k, V v) {
mMap.put(k, v);
return this;
}
public Map<K, V> build() {
return mMap;
}
}
사용법을 알 수식하다new MapBuilder<String, Object>().put("a", 1).put("b", "foo").build();
단, 현재 사용하고 있는 솔루션에서는 varargs와 vargs 와Pair
클래스:
public class Maps {
public static <K, V> Map<K, V> of(Pair<K, V>... pairs) {
Map<K, V> = new HashMap<>();
for (Pair<K, V> pair : pairs) {
map.put(pair.first, pair.second);
}
return map;
}
}
Map<String, Object> map = Maps.of(Pair.create("a", 1), Pair.create("b", "foo");
의 장황함Pair.create()
좀 신경 쓰이긴 하지만, 이건 꽤 잘 작동해요.스태틱 Import에 문제가 없다면 도우미를 만들 수 있습니다.
public <K, V> Pair<K, V> p(K k, V v) {
return Pair.create(k, v);
}
Map<String, Object> map = Maps.of(p("a", 1), p("b", "foo");
(대신Pair
사용하는 것을 상상할 수 있다Map.Entry
단, 인터페이스이므로 구현 클래스 및/또는 도우미 팩토리 메서드가 필요합니다.또한 불변하지 않으며 이 작업에는 유용하지 않은 다른 논리가 포함되어 있습니다.)
Streams In Java 8 을 사용할 수 있습니다(이것은 세트의 exmaple 입니다).
@Test
public void whenInitializeUnmodifiableSetWithDoubleBrace_containsElements() {
Set<String> countries = Stream.of("India", "USSR", "USA")
.collect(collectingAndThen(toSet(), Collections::unmodifiableSet));
assertTrue(countries.contains("India"));
}
참고 자료: https://www.baeldung.com/java-double-brace-initialization
다음 예시와 같이 맵을 초기화하는 방법을 작성할 수 있습니다.
Map<String, Integer> initializeMap()
{
Map<String, Integer> ret = new HashMap<>();
//populate ret
...
return ret;
}
//call
Map<String, Integer> map = initializeMap();
Java 8에서는 다음 코드를 사용할 수 있습니다.
Map<String, Integer> map = Stream.of(new Object[][] {
{ "data1", 1 },
{ "data2", 2 },
}).collect(Collectors.toMap(data -> (String) data[0], data -> (Integer) data[1]));
크레딧:
Map.of()
가장 보편적이고 가장 제한적이지 않은 것 같습니다.여기서는 오브젝트 이외의 입력값을 자동으로 처리합니다.
List<Map<String, Object> certs = new ArrayList<>(){{ add( Map.of(
"TAG", Obj1 // Object
"TAGGED_ID", 1L //Long
"DEGREE", "PARENT" // String
"DATE", LocalDate.now() // LocalDate
));}};
static에 의해 작성된 맵에 주의해당 맵은Map.of(..)
변환기는 키도 값도 허용하지 않습니다.null
.
다양한 Java 버전에서 이를 수행하는 몇 가지 방법을 나열한 beldung의 훌륭한 기사를 찾았습니다.
편리한 몇 가지 흥미로운 방법은 다음과 같습니다.
임의의 Java 버전
public static Map<String, String> articleMapOne;
static {
articleMapOne = new HashMap<>();
articleMapOne.put("ar01", "Intro to Map");
articleMapOne.put("ar02", "Some article");
}
스트림을 사용하는 Java 8의 경우
Map<String, String> map = Stream.of(new String[][] {
{ "Hello", "World" },
{ "John", "Doe" },
}).collect(Collectors.toMap(data -> data[0], data -> data[1]));
언급URL : https://stackoverflow.com/questions/6802483/how-to-directly-initialize-a-hashmap-in-a-literal-way
'itsource' 카테고리의 다른 글
Vuex Store는 이름에 snake_case 또는 camelCase 중 어느 것을 사용해야 합니까? (0) | 2022.08.29 |
---|---|
C 함수에서 문자열을 반환하는 중 (0) | 2022.08.29 |
nuxt에서 vue-chartjs에서 이 오류가 발생하는 이유는 무엇입니까? (0) | 2022.08.29 |
vue 프로젝트에서 blob 및 FileSaver.js를 사용하여 excel(.xlsx)을 다운로드하고 있습니다. (0) | 2022.08.29 |
Vuex를 사용하여 데이터베이스에서 상태를 처음 로드하는 시기 (0) | 2022.08.29 |