JavaRush /Java Blog /Random-TL /Pagbabalot, pag-unwrap at pag-iimpake

Pagbabalot, pag-unwrap at pag-iimpake

Nai-publish sa grupo
Kamusta! Medyo pamilyar ka na sa mga primitive na uri, at marami ka nang nakatrabaho sa kanila. Pagbabalot, pag-unwrap at pag-iimpake - 1Ang mga primitive sa programming, at partikular sa Java, ay may maraming mga pakinabang: kumukuha sila ng kaunting memorya, sa gayon ay pinapataas ang kahusayan ng programa, at malinaw na nahahati sa mga hanay ng mga halaga. Gayunpaman, sa proseso ng pag-aaral ng Java, inulit namin ang higit sa isang beses, tulad ng isang mantra, " sa Java ang lahat ay isang bagay ." Ngunit ang mga primitive ay isang direktang pagtanggi sa mga salitang ito. Hindi sila bagay. Kaya ang prinsipyo na "lahat ay isang bagay" ay mali? Hindi naman. Sa Java, ang bawat primitive na uri ay may kambal nitong kapatid, ang klase ng wrapper ( Wrapper). Ano ang isang wrapper? Ang wrapper ay isang espesyal na klase na nag-iimbak ng halaga ng primitive sa loob mismo. Ngunit dahil isa itong klase, maaari itong lumikha ng sarili nitong mga pagkakataon. Iimbak nila ang mga kinakailangang primitive na halaga sa loob, habang sila ay tunay na mga bagay. Ang mga pangalan ng mga klase ng wrapper ay halos kapareho sa mga pangalan ng kaukulang primitives, o ganap na nag-tutugma sa kanila. Samakatuwid, magiging napakadaling matandaan ang mga ito.
Mga Klase ng Wrapper para sa Primitive na Mga Uri ng Data
Mga Uri ng Primitive na Data Mga Klase ng Wrapper
int Integer
maikli Maikli
mahaba Mahaba
byte Byte
lumutang Lumutang
doble Doble
char karakter
boolean Boolean
Ang mga bagay sa klase ng wrapper ay nilikha tulad ng iba pa:
public static void main(String[] args) {

   Integer i = new Integer(682);

   Double d = new Double(2.33);

   Boolean b = new Boolean(false);
}
Binibigyang-daan ka ng mga klase ng wrapper na pagaanin ang mga disadvantage na mayroon ang mga primitive na uri. Ang pinaka-halata ay ang mga primitive ay walang mga pamamaraan . Halimbawa, wala silang paraan toString(), kaya hindi mo, halimbawa, i-convert ang isang numero intsa isang string. Ngunit sa isang klase ng wrapper Integermadali ito.
public static void main(String[] args) {

   Integer i = new Integer(432);

   String s = i.toString();
}
Magkakaroon din ng mga paghihirap sa reverse transformation. Sabihin nating mayroon tayong string na alam nating tiyak na naglalaman ng numero. Gayunpaman, sa kaso ng isang primitive na uri, inthindi namin makukuha ang numerong ito mula sa string at gawing numero ito, sa katunayan. Ngunit salamat sa mga klase ng wrapper, mayroon na tayong pagkakataong ito.
public static void main(String[] args) {

   String s = "1166628";

   Integer i = Integer.parseInt(s);

   System.out.println(i);
}
Output: 1166628 Matagumpay naming nakuha ang isang numero mula sa isang string at itinalaga ito sa isang reference variable Integer i. Sa pamamagitan ng paraan, tungkol sa mga link. Alam mo na na ang mga parameter ay ipinapasa sa mga pamamaraan sa iba't ibang paraan: ang mga primitive ay ipinapasa sa pamamagitan ng halaga, at ang mga bagay ay ipinasa sa pamamagitan ng sanggunian. Magagamit mo ang kaalamang ito kapag lumilikha ng iyong mga pamamaraan: kung gumagana ang iyong pamamaraan, halimbawa, sa mga fractional na numero, ngunit kailangan mo ng lohika ng pagpasa sa pamamagitan ng sanggunian, maaari mong ipasa ang mga parameter sa pamamaraan Double/Floatsa halip na double/float. Bilang karagdagan, bilang karagdagan sa mga pamamaraan, ang mga klase ng wrapper ay may mga static na field na napaka-maginhawang gamitin. Halimbawa, isipin na nahaharap ka na ngayon sa isang gawain: i-print ang maximum na posibleng numero sa console int, at pagkatapos ay ang pinakamababang posibleng numero. Ang gawain ay tila elementarya, ngunit gayunpaman, halos hindi mo ito magagawa nang walang Google. At madaling nagbibigay-daan sa iyo ang mga klase ng wrapper na lutasin ang mga sumusunod na "pang-araw-araw na problema":
public class Main {
   public static void main(String[] args) {

       System.out.println(Integer.MAX_VALUE);
       System.out.println(Integer.MIN_VALUE);
   }
}
Ang ganitong mga patlang ay nagbibigay-daan sa iyo na hindi magambala mula sa mas seryosong mga gawain. Hindi sa banggitin ang katotohanan na sa proseso ng pag-print ng numero 2147483647 (ito ay eksaktong MAX_VALUE) hindi nakakagulat na mali ang pag-type nito :) Bilang karagdagan, sa isa sa mga nakaraang lektura ay nakuha na namin ang pansin sa katotohanan na ang mga bagay ng mga klase ng wrapper ay hindi nababago .
public static void main(String[] args) {

   Integer a = new Integer(0);
   Integer b = new Integer(0);

   b = a;
   a = 1;
   System.out.println(b);
}
Output: 0 Ang bagay na orihinal na itinuro ng sanggunian аay hindi nagbago ng estado nito, kung hindi bay magbabago rin ang halaga. Tulad ng sa String, sa halip na baguhin ang estado ng wrapper object, isang ganap na bagong object ay nilikha sa memorya. Bakit sa huli ay nagpasya ang mga tagalikha ng Java na panatilihin ang mga primitive na uri sa wika? Dahil ang lahat ay dapat na isang bagay, at mayroon na tayong mga klase ng wrapper na magagamit upang ipahayag ang lahat ng ipinahahayag ng mga primitive, bakit hindi na lang iwanan ang mga ito sa wika at alisin ang mga primitive? Ang sagot ay simple - pagganap. Ang mga primitive na uri ay tinatawag na primitive dahil wala silang maraming "mabigat" na katangian ng mga bagay. Oo, ang isang bagay ay may maraming maginhawang pamamaraan, ngunit hindi mo palaging kailangan ang mga ito. Minsan kailangan mo lang ng numero 33, o 2.62, o ang halaga ng true/ false. Sa mga sitwasyon kung saan ang lahat ng mga benepisyo ng mga bagay ay hindi mahalaga at hindi kinakailangan para sa programa upang gumana, ang mga primitive ay gagawa ng isang mas mahusay na trabaho.

Auto-packing/auto-unpacking

Ang isa sa mga tampok ng mga primitive at ang kanilang mga klase ng wrapper sa Java ay ang autoboxing/autounboxing. Pagbabalot, pag-unwrap at pag-iimpake - 2 Unawain natin ang konseptong ito. Tulad ng natutunan mo at ko kanina, ang Java ay isang object-oriented na wika. Nangangahulugan ito na ang lahat ng mga program na nakasulat sa Java ay binubuo ng mga bagay. Ang mga primitive ay hindi mga bagay. Gayunpaman, ang variable ng klase ng wrapper ay maaaring magtalaga ng isang halaga ng isang primitive na uri. Ang prosesong ito ay tinatawag na autoboxing . Sa parehong paraan, ang isang variable ng isang primitive na uri ay maaaring italaga ng isang bagay ng isang klase ng wrapper. Ang prosesong ito ay tinatawag na autounboxing . Halimbawa:
public class Main {
   public static void main(String[] args) {
       int x = 7;
       Integer y = 111;
       x = y; // auto unpacking
       y = x * 123; // autopacking
   }
}
Sa linya 5, itinalaga namin ang primitive x ang halaga ng y, na isang bagay ng klase ng wrapper Integer. Gaya ng nakikita mo, walang karagdagang aksyon ang kailangan para dito: alam iyon ng compiler intat Integer, sa katunayan, ang parehong bagay . Ito ay awtomatikong pag-unpack. Ang parehong bagay ay nangyayari sa autoboxing sa linya 6: object y ay madaling itinalaga ang halaga ng primitives (x*123). Ito ay isang halimbawa ng autopacking. Ito ang dahilan kung bakit idinagdag ang salitang "auto": upang magtalaga ng mga primitive na sanggunian sa mga bagay ng kanilang mga klase ng wrapper (at vice versa) hindi mo kailangang gumawa ng anuman, lahat ay awtomatikong nangyayari . Maginhawa, tama? :) Ang isa pang napakahusay na kaginhawahan ng auto-packing/auto-unpacking ay makikita sa pagpapatakbo ng mga pamamaraan. Ang katotohanan ay ang mga parameter ng pamamaraan ay napapailalim din sa autopacking at autounpacking . At, halimbawa, kung ang isa sa kanila ay kukuha ng dalawang bagay bilang input Integer, madali nating maipapasa ang mga ordinaryong primitive doon int!
public class Main {
   public static void main(String[] args) {

       printNumber(7);//regular int, even without a variable
   }

   public static void printNumber(Integer i) {
       System.out.println("You entered a number" + i);
   }
}
Output: Inilagay mo ang numero 7. Ito ay gumagana sa kabaligtaran:
public class Main {
   public static void main(String[] args) {

       printNumber(new Integer(632));
   }

   public static void printNumber(int i) {
       System.out.println("You entered a number" + i);
   }
}
Isang mahalagang punto na dapat tandaan: ang autoboxing at unboxing ay hindi gumagana para sa mga array !
public class Main {
   public static void main(String[] args) {

       int[] i = {1,2,3,4,5};

       printArray(i);//error, won't compile!
   }

   public static void printArray(Integer[] arr) {
       System.out.println(Arrays.toString(arr));
   }
}
Ang pagsisikap na magpasa ng hanay ng mga primitive sa isang paraan na kumukuha ng hanay ng mga bagay bilang input ay magdudulot ng error sa compilation. Sa wakas, muli nating maikli na ihambing ang mga primitive at wrapper na Primitives:
  • magkaroon ng kalamangan sa pagganap
Mga wrapper:
  • Pinapayagan ka nilang huwag labagin ang prinsipyong "lahat ay isang bagay", upang ang mga numero, simbolo at boolean na halaga ay totoo/mali ay hindi mahulog sa konseptong ito.
  • Palawakin ang kakayahang magtrabaho kasama ang mga halagang ito sa pamamagitan ng pagbibigay ng mga maginhawang pamamaraan at larangan
  • Kinakailangan kapag ang ilang pamamaraan ay maaaring gumana nang eksklusibo sa mga bagay
Mga komento
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION