-
Massivin ArrayList -ə çevrilməsi .
Massivi ArrayList -ə çevirmək üçün tərtibatçılar tez-tez bu üsuldan istifadə edirlər:
List<String> list = Arrays.asList(arr);
Arrays.asList()
sinfinArrayList
daxili özəl statik sinfi olan sinif obyektini qaytaracaq və bu sinif deyil Sinifdə , , metodları var , lakin elementlərin əlavə edilməsi üçün heç bir üsul yoxdur, ölçüsü sabitdir . Həqiqi bir yaratmaq üçün bunu edin:(private static class)
Arrays
java.util.ArrayList.
java.util.Arrays.ArrayList
set()
get()
contains()
java.util.ArrayList
ArrayList<String> arrayList = new ArrayList<String>(Arrays.asList(arr));
Sinif konstruktoru
java.util.ArrayList
interfeysi həyata keçirən bütün obyektləri parametr kimi qəbul edə bilərCollection
, onun həyata keçirilməsi sinfə miras qalmışdır.java.util.Arrays.ArrayList
(özəl statik sinif ArrayList<E> AbstractList-i genişləndirir<E> RandomAccess, java.io.Serializable tətbiq edir).
-
Müəyyən bir dəyər üçün massiv yoxlanılır.
Tərtibatçılar tez-tez bunu edirlər:
Set<String> set = new HashSet<String>(Arrays.asList(arr)); return set.contains(targetValue);
List
Kod işləyir, lakin onu -a çevirməyə ehtiyac yoxdurSet
. ÇevirməkSet
əlavə vaxt aparacaq. Əslində hər şey sadədir:Arrays.asList(arr).contains(targetValue);
və ya
for(String s: arr){ if(s.equals(targetValue)) return true; } return false;
Birinci üsul daha qısadır.
-
List
Döngədən elementin çıxarılmasıDöngədə elementləri silən aşağıdakı kodu nəzərdən keçirin:
ArrayList<String> list = new ArrayList<String>(Arrays.asList("a", "b", "c", "d")); for (int i = 0; i < list.size(); i++) { list.remove(i); } System.out.println(list);
Nəticə:
[b, d]
Bunun ciddi bir səhv olduğu ortaya çıxır. Element çıxarıldıqda ölçüsü
List
azalır və element indeksləri dəyişir.Beləliklə, indeksdən istifadə edərək bir döngədə çoxlu elementləri silmək istəyirsinizsə, bu üsuldan qaçın.
Siz bilə bilərsiniz ki, iteratordan istifadə etmək döngədə elementləri silmək üçün düzgün həll yoludur və siz bilirsiniz ki, stil döngəsi
for-each
iterator kimi işləyir, lakin o deyil.Aşağıdakı kodu nəzərdən keçirin:
ArrayList<String> list = new ArrayList<String>(Arrays.asList("a", "b", "c", "d")); for (String s : list) { if (s.equals("a")) list.remove(s); }
Biz ConcurrentModificationException alacağıq .
Ediləcək düzgün şey:
ArrayList<String> list = new ArrayList<String>(Arrays.asList("a", "b", "c", "d")); Iterator<String> iter = list.iterator(); while (iter.hasNext()) { String s = iter.next(); if (s.equals("a")) { iter.remove(); } }
Metoddan
Döngü üslubundanext()
əvvəl çağırılmalıdırremove()
.for-each
kompilyator metodu çağıracaqremove()
və yalnız bundan sonranext()
xəta yaradacaqConcurrentModificationException
. Koda baxa bilərsinizArrayList.iterator()
. -
Hashtable
qarşıHashMap
.Müvafiq icraya görə Hashtable verilənlər strukturunun adıdır.
Lakin Java -da verilənlər strukturunun adı
HashMap
.Hashtable
və arasındakı əsas fərqlərdən biri sinxronizasiyaHashMap
olmasıdır.Ona görə də haradaHashtable
istifadə edilməməlidir .Hashtable
HashMap
-
Kolleksiyaları məzmun məhdudiyyəti olmadan istifadə edin
В Java часто путают коллекции без ограничений по содержимому, и коллекции с маской по типу содержимого. К примеру, для множеств -
Set
это коллекция без ограничений по содержимому, аSet<?>
— коллекция у которой все-таки есть ограничения, но эти ограничения ничего на самом деле не ограничивают. Рассмотрим следующий code, гдеList
без ограничений используется в качестве параметра метода:public static void add(List list, Object o){ list.add(o); } public static void main(String[] args){ List<String> list = new ArrayList<String>(); add(list, 10); String s = list.get(0); }
Данный code выбросит исключение:
Exception in thread "main" java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.String at …
Использование коллекций без ограничений по содержимому очень опасно, потому что вы не можете быть уверенными в том что там лежит внутри. А для того чтобы понять всю глубину разницы между
Set
,Set<?>
иSet<Object>
— почитайте вот эту и эту ссылки. -
Уровень доступа
Очень часто для полей класса разработчики используют модификатор доступа
public
. Так проще получить meaning поля напрямую. Правильнее использовать How можно более ограниченный доступ к членам класса. ArrayList
противLinkedList
Когда разработчики не знают чем отличается
ArrayList
отLinkedList
, они используют первый в силу его большей известности. Однако, есть огромная разница в производительности между ними. На самом деле, выбор между ними должен быть продиктован их внутренними особенностями —ArrayList
позволяет быстро производить доступ к произвольному элементу массива, аLinkedList
— быстро добавлять/удалять элементы в массиве. Почитайте статью по ссылке ArrayList vs. LinkedList чтобы понять причины их разной производительности.Mutable
(Изменяемый) противImmutable
(Неизменяемый)Неизменяемый an object имеет много преимуществ: простота, безопасность и т.д. Но он требует отдельного an object для каждого нового значения, и за слишком большое количество an objectов придется заплатить понижением производительности. Должен быть баланс при выборе между изменяемым и неизменяемым обьектом.
В основном чтобы избежать подготовки промежуточных an objectов используется изменяемый an object. Один из классических примеров это конкатенация большого количества строк. Если вы используете неизменяемый an object типа
String
, то вы создаете много an objectов, которые сразу попадут в сборщик мусора. Это тратит время и энергию процессора, поэтому правильное решение это использование изменяемых обьектов (напримерStringBuilder
).String result=""; for(String s: arr){ result = result + s; }
Еще один пример использования изменяемых an objectов — передача такого an object в метод. Это позволит вернуть результат в нем же, без создания лишних an objectов. При работе с an objectми большого размера, к примеру коллекциями, передача коллекции в метод для сортировки и возвращение результата в другой коллекции приводит к совершенно излишнему расходу ресурсов. (Ответ пользователя dasblinkenlight на Stack Overflow).
-
Конструкторы классов
Super
иSub
Bu kompilyasiya xətası, əcdad sinfində müəyyən edilmiş standart konstruktorun olmaması ilə əlaqədardır. Java - da siz özünüz sinif konstruktoru təyin etməsəniz, kompilyator heç bir arqument tələb etməyən standart konstruktor yaradacaq. Konstruktor sinifdə
Super
kimi təsvir edilirsəSuper(String s){}
, kompilyator özü heç nə əlavə etməyəcək. Bizim nümunəmizdə gördüyümüz budur.Sinfin konstruktoru
Sub
, hansının olmasından asılı olmayaraq, sinfin standart konstruktorunu çağıracaqSuper
, çünki başqa heç nə göstərilməyib. Sinifdə standart konstruktor olmadığı üçünSuper
bu kompilyasiya xətasına gətirib çıxaracaq.Bu problemin ilk həlli sinifə standart konstruktor əlavə etməkdir
Super
public Super(){ System.out.println("Super"); }
İkinci seçim, təsvir etdiyimiz konstruktoru sinifdən çıxarmaqdır
Super
ki, kompilyator standart konstruktor yaratsın.super(value)
Və son seçim sinif konstruktorlarına zəng əlavə etməkdirSub
ki, standart konstruktor əvəzinə mövcud sinif konstruktoru çağırılsın.Super
-
" " yoxsa konstruktor?
Bir sətir yaratmağın iki yolu var:
//1. использовать двойные кавычки String x = "abc";
//2. использовать конструктор String y = new String("abc");
Onların arasındakı fərq nədir?
Bunu aşağıdakı nümunələrdən başa düşə bilərsiniz:
String a = "abcd"; String b = "abcd"; System.out.println(a == b); // True System.out.println(a.equals(b)); // True String c = new String("abcd"); String d = new String("abcd"); System.out.println(c == d); // False System.out.println(c.equals(d)); // True
Sətirlərin yaddaşda necə saxlanması haqqında daha çox öyrənmək üçün oxuyun "" və ya Konstruktordan istifadə edərək Java sətrini yaradın? .
GO TO FULL VERSION