มีวิธีใดบ้างในการประกาศอาร์เรย์ในบรรทัด


617

สมมติว่าฉันมีเมธอด m () ที่รับอาเรย์ของสตริงเป็นอาร์กิวเมนต์ มีวิธีที่ฉันสามารถประกาศอาร์เรย์นี้ในบรรทัดเมื่อฉันโทร? ie แทน:

String[] strs = {"blah", "hey", "yo"};
m(strs);

ฉันสามารถแทนที่มันด้วยหนึ่งบรรทัดและหลีกเลี่ยงการประกาศตัวแปรที่ตั้งชื่อที่ฉันจะไม่ใช้หรือไม่


2
IDE ที่รองรับแฟคตอริ่งใหม่จะช่วยให้คุณสามารถ str-in-line ได้โดยอัตโนมัติ
Paul McKenzie

คำตอบ:


945
m(new String[]{"blah", "hey", "yo"});

77
สำหรับการอ้างอิงในอนาคตอาร์เรย์ประเภทนี้เรียกว่าอาเรย์ที่ไม่ระบุชื่อ (เนื่องจากไม่มีชื่อ) การค้นหา "Anonymous array java" จะให้ผลลัพธ์บางอย่าง
Falaina

2
มันคล้ายกับการคัดเลือกนักแสดง ฉันคิดว่าฉันจะคิดอย่างไรฉันจึงไม่ต้อง google ในครั้งเดียวใน bluemoon ฉันต้องทำสิ่งนี้
ArtOfWarfare

นี่เป็นตัวอย่างที่หาได้ยากซึ่งคำตอบเฉพาะโค้ดเท่านั้นเป็นที่ยอมรับกันโดยสิ้นเชิงและในความเป็นจริงแล้วอาจเป็นที่นิยมมากกว่า
Max von Hippel

113

Draemon ถูกต้อง นอกจากนี้คุณยังสามารถประกาศmว่ารับค่าvarargs :

void m(String... strs) {
    // strs is seen as a normal String[] inside the method
}

m("blah", "hey", "yo"); // no [] or {} needed; each string is a separate arg here

19
ไวยากรณ์ที่ค่อนข้างดี แต่ด้วยวิธีนี้คุณสามารถมีพารามิเตอร์อาร์เรย์ได้เพียงพารามิเตอร์เดียวเท่านั้นและต้องเป็นพารามิเตอร์สุดท้าย void m(String... strs, Integer... intgrs)ตัวอย่างเช่นคุณไม่สามารถทำได้
bluefoot

5
Blefoot ถูกต้อง แต่คุณสามารถทำได้void m(Integer i, Double d, String... str)
Igor S.

(String ... strs)
@MichaelMyers

1
@KasunSiyambalapitiya: คลิกลิงก์ในคำตอบของฉัน
Michael Myers

30

อีกวิธีหนึ่งในการทำเช่นนั้นหากคุณต้องการให้ผลลัพธ์เป็นรายการแบบอินไลน์คุณสามารถทำได้ดังนี้:

Arrays.asList(new String[] { "String1", "string2" });

38
คุณไม่จำเป็นต้องสร้างอาร์เรย์คุณสามารถทำได้ง่ายๆ:Arrays.asList("string1", "string2", ...)
Elias Dorneles

2
จุดที่มีประโยชน์อาจเป็นไปได้: คุณไม่สามารถทำสิ่งนี้ได้ด้วยวิธีดั้งเดิม คุณจะจบลงด้วยองค์ประกอบเดียวListของtype[]ที่typeเป็นแบบดั้งเดิมที่ เช่นผลในArrays.asList([some ints]) List<int[]>
Moira

@ อันโตนิโอคาร์ลอ: ไม่มันไม่ได้เป็น คุณสามารถโทรsetกลับListและมันจะแก้ไขอาร์เรย์
Holger

17

คุณสามารถเขียนอาเรย์ใน Java สมัยใหม่ได้โดยตรงโดยไม่ต้องมี initializer ตัวอย่างของคุณถูกต้องแล้ว เป็นการดีที่สุดที่จะตั้งชื่อพารามิเตอร์ต่อไป

String[] array = {"blah", "hey", "yo"};

หรือ

int[] array = {1, 2, 3};

หากคุณต้องอินไลน์คุณจะต้องประกาศประเภท:

functionCall(new String[]{"blah", "hey", "yo"});

หรือใช้ varargs (อาร์กิวเมนต์ตัวแปร)

void functionCall(String...stringArray) {
    // Becomes a String[] containing any number of items or empty
}

functionCall("blah", "hey", "yo");

หวังว่านักพัฒนา Java จะอนุญาตให้เริ่มต้นโดยนัยในอนาคต

Update: Kotlin คำตอบ

Kotlin ทำให้การทำงานกับอาร์เรย์ง่ายขึ้นมาก! สำหรับประเภทส่วนใหญ่เพียงใช้arrayOfและมันจะกำหนดประเภทโดยปริยาย ผ่านไม่มีอะไรจะปล่อยให้พวกเขาว่างเปล่า

arrayOf("1", "2", "3") // String
arrayOf(1, 2, 3)       // Int
arrayOf(1, 2, "foo")   // Any 
arrayOf<Int>(1, 2, 3)  // Set explict type
arrayOf<String>()      // Empty String array

ดึกดำบรรพ์มีฟังก์ชั่นยูทิลิตี้ ผ่านไม่มีอะไรจะปล่อยให้พวกเขาว่างเปล่า

intArrayOf(1, 2, 3)
charArrayOf()
booleanArrayOf()
longArrayOf()
shortArrayOf()
byteArrayOf()

หากคุณมีCollectionและต้องการที่จะแปลงเป็นอินไลน์อาร์เรย์ให้ใช้:

collection.toTypedArray()

หากคุณต้องการบีบบังคับประเภทอาเรย์ให้ใช้:

array.toIntArray()
array.toLongArray()
array.toCharArray()
...

แต่คุณทำไม่ได้doSomething({"blah", "hey", "yo"})ซึ่งเป็นคำถามเดิมที่ถาม
David DeMar

11

คุณสามารถสร้างวิธีการบางแห่ง

public static <T> T[] toArray(T... ts) {
    return ts;
}

จากนั้นใช้มัน

m(toArray("blah", "hey", "yo"));

เพื่อให้ดูดีขึ้น


3

ฉันต้องการเพิ่มว่าไวยากรณ์การกำหนดค่าเริ่มต้นของอาร์เรย์นั้นรวบรัดและยืดหยุ่นมาก ฉันใช้มันเป็นจำนวนมากเพื่อดึงข้อมูลจากรหัสของฉันและวางไว้ที่อื่นที่สามารถใช้งานได้มากกว่า

ตัวอย่างเช่นฉันมักจะสร้างเมนูแบบนี้:

Menu menu=initMenus(menuHandler, new String[]{"File", "+Save", "+Load", "Edit", "+Copy", ...});

สิ่งนี้จะช่วยให้ฉันเขียนรหัสมาเพื่อตั้งค่าระบบเมนู เครื่องหมาย "+" ก็เพียงพอที่จะบอกให้วางรายการนั้นไว้ใต้รายการก่อนหน้า

ฉันสามารถผูกมันไว้กับคลาส menuHandler โดยวิธีการตั้งชื่อเมธอดโดยตั้งชื่อเมธอดของฉันบางอย่างเช่น "menuFile, menuFileSave, menuFileLoad, ... " และเชื่อมโยงพวกเขาอย่างไตร่ตรอง (มีทางเลือกอื่น ๆ )

ไวยากรณ์นี้อนุญาตนิยามเมนูย่อแบบ AMAZINGLY และเมธอด "initMenus" ที่นำกลับมาใช้ใหม่ได้ (ถึงกระนั้นฉันก็ไม่ได้ใช้ซ้ำเพราะมันสนุกเสมอในการเขียนและใช้เวลาเพียงไม่กี่นาที + โค้ดสองสามบรรทัด)

เมื่อใดก็ตามที่คุณเห็นรูปแบบในรหัสของคุณดูว่าคุณสามารถแทนที่มันด้วยสิ่งนี้และจำไว้เสมอว่าไวยากรณ์การเริ่มต้นอาร์เรย์นั้นสั้นกระชับแค่ไหน!


5
สิ่งนี้จะดีกว่าที่จะทำในรูปแบบ varargs นอกจากนี้ทุกคนที่ชอบพิมพ์รหัสเพื่อ "สนุก" ควรได้รับการโหวตลง! การเข้ารหัสคือการแก้ปัญหาใหม่ไม่ใช่การพิมพ์ โอ้เดี๋ยวก่อนนี่คือ Java ;-)
mjaggard

1
คุณถูกต้องเมื่อฉันเขียนสิ่งนี้ฉันไม่ได้ใช้ varargs มากนัก - และฉันใช้การกำหนดค่าเริ่มต้นของอาเรย์ค่อนข้างน้อยก่อนที่จะมี varargs ในจาวา ส่วนหนึ่งที่ฉันต้องการยังคงเป็นอาร์เรย์สำหรับถ้าคุณกำหนดเป็นอาเรย์คุณสามารถทำให้มันคงที่ด้านบนของไฟล์แทนข้อมูลแบบอินไลน์และคุณยังสามารถแยกมันเป็นไฟล์ config
Bill K

อย่างไรก็ตาม 8 ปีต่อมาฉันต้องบอกว่าตอนนี้ฉันพบว่าตัวเองกำลังใช้คำอธิบายประกอบเพื่อทำเกือบทุกสิ่งที่ฉันเคยใช้ในการเริ่มต้นอาร์เรย์สตริง
Bill K

2

ตัวเลือกอื่นคือใช้ ArrayUtils.toArray ใน org.apache.commons.lang3

ArrayUtils.toArray("elem1","elem2")

เป็นทางเลือก แต่มีการเรียกใช้ฟังก์ชันเพิ่มเติมที่เพิ่มไปยังสแต็กซึ่งไม่จำเป็น
CybeX

1

ดังที่ Draemon กล่าวว่าสิ่งที่ใกล้เคียงที่สุดที่ Java มาถึง inline arrays คือnew String[]{"blah", "hey", "yo"}อย่างไรก็ตามมีกลอุบายที่ช่วยให้คุณทำสิ่งต่าง ๆ เช่น

array("blah", "hey", "yo") ด้วยประเภทที่อนุมานโดยอัตโนมัติ

ฉันทำงานกับ API ที่มีประโยชน์สำหรับการเพิ่มภาษา Java เพื่ออนุญาตให้ใช้อาร์เรย์แบบอินไลน์และประเภทการรวบรวม สำหรับรายละเอียดเพิ่มเติมของโครงการ Google Espresso4J หรือตรวจสอบได้ที่นี่


9
เพียงไม่กี่ปัญหาที่นี่: 1. โปรดตรวจสอบให้แน่ใจว่าในโพสต์และโปรไฟล์ของคุณคุณทำให้ชัดเจนว่าคุณมีส่วนเกี่ยวข้องกับ Espresso4J (โปรดดูคำถามที่พบบ่อยของเรา) 2. โปรดระมัดระวังลิงค์โพสต์ไปยังเว็บไซต์ของคุณเอง โดยเฉพาะอย่างยิ่งคำตอบสำเร็จรูปอย่างนี้และนี้ ) - มันออกมาเป็นสแปมมากและยกธงซึ่งจะบุ๋มตัวแทนของคุณ
Kev

@Kev อาขอโทษ ฉันชี้แจงว่าฉันเป็นผู้พัฒนาโครงการ Espresso4J ที่ดีในตอนนี้ :)
Jonathan Weatherhead
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.