Java로 세트는 중복 요소를 포함하지 않거나 E1.equals (E2)를 포함하지 않는 요소 쌍의 세트입니다. NULL은 세트에 허용됩니다. 세트는 세트의 요소 순서를 보장 할 수 없습니다.
설정에 요소를 추가 할 때 지정된 요소가 존재하지 않으면 추가가 성공적입니다. 즉, 요소 E1이 세트에 존재하지 않으면 (e == null? e1 == null : e.queals (e1)), E1을 세트에 추가 할 수 있습니다.
다음은 예제로 설정된 구현 클래스 해시 세트이며, 구현을 반복하지 않도록 설정의 원칙을 간략하게 소개합니다.
package com.darren.test.overide; public class customstring {private String value; public customstring () {this ( "");} public customstring (문자열 값) {this.value = value;}} package com.darren.test.overide; import java.util.hashset; import java.util.set; public class hashsettest {public static void main (string [] args) {string a = new String ( "A"); String B = 새 문자열 ( "A"); New CustomString ( "B"); customString ( "b"); system.out.println ( "a.equals (b) ==" + a.equals (b)); system.out.println ( "c.equals (d) ==" + c.equals (d)); set <bood> set = new hashset <botor> (); set.add (a); set.add (b); set.add (c); set.add (d); system.out.println ( "set.size () ==" + set.size ()); for (object : set) {system.out.println (Object);}}}작업 결과는 다음과 같습니다.
a.equals (b) == true c.equals (d) == false set.size () == 3 com.darren.test.overide.customstring@2c39d2 a com.darren.test.overide.customstring@5795ce
어쩌면 당신은 열쇠를 보았을 수도 있습니다. 맞습니다. 그것은 평등 방법입니다. 이것을 말하는 것은 여전히 부적절하지만 정확하기 위해서는 평등하고 해시 코드 방법이어야합니다. 왜 그렇게 말합니까? CustomString 클래스를 변경하고 테스트합시다.
packet com.darren.test.overide; public class customstring {private String value; public customstring () {this ( "");} public customString (string value) {this.value = value;}@public boolean Equals (객체 obj) {if (this == obj) {return true; if (custommentString) {custommentString) obj; return customstring.value.equals (value);} else {return false;}}}}테스트 결과 :
a.equals (b) == true c.equals (d) == true set.size () == 3 com.darren.test.overide.customstring@12504e0 a com.darren.test.overide.customstring@1630eb6
이 시간의 반환 값은 사실이지만 세트의 크기는 여전히 3입니다.
계속 바꾸자
package com.darren.test.overide; public class customstring {private String value; public customstring () {this ( "");} public customstring (string value) {this.value = value;}@public int hashcode () {// return super.hashcode (); 반환 1;}}결과를 다시보십시오.
a.equals (b) == true c.equals (d) == false set.size () == 3 com.darren.test.overide.customstring@1 com.darren.test.overide.customstring@1 A
해시 코드 메소드 만 다시 작성하지 않고 Equals 메소드를 다시 작성하지 않습니다
마지막으로 변경하십시오
packet com.darren.test.overide; public class customstring {private String value; public customstring () {this ( "");} public customString (string value) {this.value = value;}@public boolean Equals (객체 obj) {if (this == obj) {return true; if (custommentString) {custommentString) obj; return customstring.value.equals (value);} else {return false;}}@public int hashcode () {// return super.hashcode (); 반환 1;}}최종 결과 :
a.equals (b) == true c.equals (d) == true set.size () == 2 com.darren.test.overide.customstring@1 a
좋아, Equals 메소드 및 해시 코드 메소드를 다시 작성하고 원리를 확인해야한다는 것이 증명됩니다.
java.lnag.object의 해시 코드 컨벤션 :
1. 응용 프로그램 실행 중에 객체의 평등 메소드를 비교하는 데 사용되는 정보가 수정되지 않은 경우 해시 코드 메소드는 객체에서 여러 번 호출되며 동일한 정수를 지속적으로 반환해야합니다.
2. 두 객체가 평등 (Objecto) 메소드에 따라 같으면 두 객체 중 하나의 해시 코드 메소드를 호출하면 동일한 정수 결과를 생성해야합니다.
3. 두 객체가 평등 (객체) 메소드에 따라 같지 않으면 두 객체 중 하나의 해시 코드 메소드가 호출되며 다른 정수 결과가 필요하지 않습니다. 그러나 다르면 해시 테이블의 성능이 향상 될 수 있습니다.
해시 세트에서 기본 작업은 해시 층이 해시 맵을 사용하여 데이터를 저장하기 때문에 해시 맵 계층에 의해 구현됩니다. 해시 세트에 요소를 추가 할 때 먼저 요소의 해시 코드 값을 계산 한 다음이 요소의 스토리지 위치를 계산하기 위해 요소의 해시 코드 값 (요소의 해시 코드)% (Hashmap Collection의 크기) + 1을 사용하십시오. 이 위치가 비어 있으면 요소를 추가하십시오. 비어 있지 않은 경우, Equals 메소드를 사용하여 요소가 동일한지 여부를 비교하고 동등한 경우 추가하지 마십시오. 그렇지 않으면 빈 공간을 찾으십시오.
다음은 해시 세트 소스 코드의 일부입니다.
패키지 java.util; public class hashset <e> 확장 abstractset <e>는 <e>, clonable, java.io.serializable {static final long serialversionuid = -50247444406713321676L; // hashmap을 사용하여 해시 세트의 모든 요소를 저장합니다. 개인 과도 해시 맵 <e, 객체>지도; // 가상 객체 객체를 해시 맵의 값으로 정의 하고이 객체를 정적 최종으로 정의합니다. 개인 정적 최종 객체 present = new Object ();/*** 기본 매개 변수가없는 생성자는 빈 해시를 구성합니다. * * 실제로, 기본 레이어는 빈 해시 맵을 초기화하고 기본 초기 용량 16과 로딩 계수가 0.75를 사용합니다. */public hashset () {map = new Hashmap <e, object> ();}/*** 지정된 컬렉션의 요소가 포함 된 새 세트를 구성합니다. * * 실제 기본 레이어는 기본 부하 계수 0.75를 사용하며 지정된 * 컬렉션의 모든 요소의 초기 용량을 포함하여 해시 맵을 생성하기에 충분합니다. * @param c 그 요소는이 세트의 컬렉션에 저장됩니다. */public hashset (collection <extends e> c) {map = new Hashmap <e, object> (math.max ((int) ()/. 75f)/. 75f) + 1, 16)); addall (c);}/*** 지정된 초기 범위 및 하중 변형으로 빈 해시 세트를 구성합니다. * * 실제 기본 레이어는 해당 매개 변수와 함께 빈 해시 맵을 구성합니다. * @param 초기 범위 초기 용량. * @param loadfactor로드 계수. */public hashset (int initialcapacity, float loadfactor) {map = new Hashmap <e, object> (InitialCapacity, Loadfactor);}/*** 지정된 초기 용량으로 빈 해시를 구성합니다. * * 실제로, 기본 레이어는 해당 매개 변수 및로드 계수로드 변형이 0.75 인 빈 해시 맵을 구성합니다. * @param 초기 범위 초기 용량. */public hashset (int initialcapacity) {map = new Hashmap <e, object> (InitialCapacity);}/*** 지정된 초기 범위 및 loadfactor를 사용하여 새 빈 링크 해시 컬렉션을 구성합니다. *이 생성자는 패키지 액세스 권한이며 대중에게 노출되지 않습니다. 실제로 LinkedHashset을 지원합니다. * * 실제로, 기본 레이어는 지정된 매개 변수와 함께 빈 링크드 하쉬 맵 인스턴스를 구현할 수 있습니다. * @param 초기 범위 초기 용량. * @param loadfactor로드 계수. * @param 더미 태그. */HASHSET (int initialcapacity, float loadfactor, boolean dummy) {map = new LinkedHashMap <e, object> (초기 범위, loadfactor);}/***이 세트의 요소를 반복하는 반복기를 반환합니다. 반환 요소의 순서는 구체적이지 않습니다. * * 기본 레이어는 실제로 모든 키를 반환하기 위해 기본 해시 맵의 키 세트를 호출합니다. * 해시 세트의 요소는 볼 수 있지만 기본 해시 맵의 키에 저장되며 값은 정적 최종 객체 객체로 식별됩니다. *이 세트의 요소를 반복하는 @return iterator. */@public iterator <e> iterator () {return map.keyset (). iterator ();}/***이 세트의 요소 수를 반환합니다 (세트의 용량). * * 기본 레이어는 실제로 해시 맵의 크기 () 메소드를 호출하여 항목 수를 반환하고 세트의 요소 수를 얻습니다. * @이 세트의 요소 수 (세트 용량). */@public int size () {return map.size ();}/***이 세트에 요소가 포함되어 있지 않으면 true return return return. * * 기본 레이어는 실제로 해시 셋이 비어 있는지 확인하기 위해 실제로 해시 맵의 ISEMPTY ()를 호출합니다. * @return이 세트에 요소가 포함되어 있지 않으면 true를 반환합니다. */@public boolean isempty () {return map.isempty ();}/***이 세트에 지정된 요소가 포함되어 있으면 true return true를 재정의합니다. *보다 구체적으로,이 세트에 (o == null? e == null : o.equals (e))를 만족시키는 e 요소가 포함 된 경우에만 true가 반환됩니다. * * 기본적으로 실제 호출에 대한 해시 맵에 포함 된 키는 지정된 키를 포함하는지 여부를 결정합니다. * @param o이 세트의 요소의 존재가 테스트되었습니다. * @return이 세트에 지정된 요소가 포함 된 경우 true reture true. */@public boolean include (object o) {return map.containskey (o);}/*** 지정된 요소 가이 세트에 포함되지 않은 경우 지정된 요소를 추가하십시오. *보다 구체적으로,이 세트 에이 세트에 만족하는 요소 E2를 포함하지 않으면 (e == null? e2 == null : eequals (e2)) *, 지정된 요소 e 가이 세트에 추가됩니다. *이 세트에 이미 요소가 포함 된 경우 호출이 세트를 변경하지 않고 False를 반환합니다. * * 기본 레이어는 실제로 요소를 키로 해시 맵에 넣습니다. * Hashmap의 put () 메소드가 키 값 쌍을 추가하기 때문에 Hashmap의 새 항목의 키가 컬렉션의 원래 항목의 키와 동일 할 때 (Hashcode ()는 동일하게 반환하고, Equals 비교를 통해 True를 반환합니다), * 새로 추가 된 항목의 값은 원래 항목의 값을 덮어 내리지 않지만 키는 변경되지 않습니다. * 따라서 기존 요소가 해시 세트에 추가되면 새로 추가 된 수집 요소가 해시 맵에 넣지 않으며 * 원래 요소는 변경되지 않으므로 세트에서 요소의 비 반복 기능을 충족시킵니다. * @param e이 세트에 추가 될 요소. * @return이 세트에 지정된 요소가 포함되어 있지 않으면 true를 반환합니다. */@public boolean add (e e) {return map.put (e, present) == null;}/*** 지정된 요소가 존재하면 제거됩니다. *보다 구체적으로,이 세트에 (o == null? e == null : o.equals (e))를 만족시키는 요소 e가 포함 된 경우 *를 제거합니다. 이 세트에 이미 요소가 포함 된 경우 true를 반환하십시오 (또는이 세트가 통화로 인해 변경된 경우 true). (통화가 돌아 오면이 세트에는 더 이상 요소가 포함되지 않습니다). * * 기본 레이어는 실제로 지정된 항목을 삭제하기 위해 해시 맵의 제거 메소드를 호출합니다. * @param o이 세트에 존재하는 경우 제거 해야하는 개체. * @return return true 세트에 지정된 요소가 포함 된 경우. */@public boolean remove (object o) {return map.remove (o) == 현재;}/***이 세트에서 모든 요소를 제거하십시오. 이 호출이 반환되면 세트가 비어 있습니다. * * 기본 레이어는 실제로 해시 맵의 명확한 방법을 호출하여 입력의 모든 요소를 지우는 것입니다. */@override public void clear () {map.clear ();}}요약
위는 중복 값의 해시 세트 제거 원리 분석에 대한이 기사의 모든 내용입니다. 모든 사람에게 도움이되기를 바랍니다. 관심있는 친구는이 사이트의 다른 관련 주제를 계속 참조 할 수 있습니다. 단점이 있으면 메시지를 남겨 두십시오. 이 사이트를 지원해 주신 친구들에게 감사드립니다!