การปรับรูปร่างทำหน้าที่ทางคณิตศาสตร์ข้อใด

ทั้งใน Python และ MATLAB คุณสามารถใช้ฟังก์ชันชื่อ reshape() เพื่อเปลี่ยนขนาดของเมทริกซ์ได้

นี่คือการดำเนินการอะไรในพีชคณิตเชิงเส้น นี่คือการเปลี่ยนแปลงของฐาน หรือการคูณเมทริกซ์ที่ง่ายกว่า หรือไม่ใช่ทั้งสองอย่างเลย?


person Steven Alsheimer    schedule 08.04.2019    source แหล่งที่มา
comment
คุณได้ดูตัวอย่างในเอกสาร reshape (MATLAB) แล้วหรือยัง   -  person SecretAgentMan    schedule 08.04.2019


คำตอบ (3)


ฟังก์ชันนี้ไม่เกี่ยวข้องกับพีชคณิตเชิงเส้น แต่เป็นเคล็ดลับง่ายๆ ในการจัดทำดัชนี พิจารณาสิ่งต่อไปนี้ (ฉันจะใช้ ไวยากรณ์ MATLAB แต่ใน Python โดยเฉพาะ เมื่อใช้ NumPy/SciPy มันจะทำหน้าที่ เดียวกัน):

A = [1 2 3; 4 5 6]; % 2-by-3 matrix
B = reshape(A,3,2); % B is 3-by-2
B =
     1     5
     4     3
     2     6

จริงๆ แล้วคุณมี 6 ดัชนีใน A: 1 ถึง 6 ตามลำดับคอลัมน์หลัก เมื่อปรับรูปร่างใหม่ สไตล์เชิงเส้นจะยังคงอยู่ เพียงแค่จัดลำดับใหม่ องค์ประกอบเชิงเส้นของคุณเรียงลำดับจากน้อยไปหามาก: 1 4 2 5 3 6 ซึ่งจัดเก็บไว้ในหน่วยความจำที่อยู่ติดกัน 'ส่วนหัว' จะบอกโปรแกรมว่าองค์ประกอบที่อยู่ติดกันเหล่านี้มีรูปร่างอย่างไร นี่คือสาเหตุที่ reshape เกือบจะว่าง: เปลี่ยนเฉพาะส่วนหัวเท่านั้น

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

หากต้องการข้อมูลเพิ่มเติมเกี่ยวกับวิธีการทำงานของการจัดทำดัชนีใน MATLAB ฉันขอแนะนำคำถาม/คำตอบที่ยอดเยี่ยมนี้

ภายใต้ประทุน MATLAB จะแปลง A(2,2) เป็น A(4) กล่าวคือ ดัชนีเชิงเส้นที่สี่ โดยใช้ sub2ind() แน่นอนเพราะว่าทุกอย่างถูกจัดเก็บเป็นเวกเตอร์เชิงเส้น การปรับรูปร่างใหม่ทั้งหมดคือการบอกส่วนหัวว่าองค์ประกอบ 3 ไม่ได้อยู่ที่ A(1,2) อีกต่อไป แต่เปลี่ยนเป็น A(3,1) เนื่องจากรูปลักษณ์เปลี่ยนไป

person Adriaan    schedule 08.04.2019
comment
มีข้อมูลอ้างอิงบ้างไหม? สิ่งที่คุณแสดงเป็นเพียงทรานสโพสง่ายๆ ฉันไม่แน่ใจว่าถ้าปรับรูปร่างที่ซับซ้อนกว่านี้ มันจะเหมือนเดิมหรือไม่ - person Karls; 08.04.2019
comment
@Karls เพียงแค่โยนสิ่งนี้ใน MATLAB การย้ายของ A จะเป็น [1 4; 2 5; 3 6] ซึ่งเป็นเมทริกซ์ที่แตกต่างจากเมทริกซ์ที่ถูกย้าย การย้ายจะเปลี่ยนลำดับขององค์ประกอบ ดังนั้นจึงมีราคาแพงกว่าการปรับรูปร่างใหม่แบบธรรมดา - person Adriaan; 08.04.2019
comment
โอเค ใช่ มันไม่เท่ากับทรานสโพส ฉันยังคิดว่ามันอาจซับซ้อนกว่าแค่ส่วนหัว คุณมีข้อมูลอ้างอิงที่สามารถสนับสนุนคำอธิบายของคุณหรือไม่? - person Karls; 08.04.2019
comment
@Karls: การอ้างอิงเป็นเอกสารของ reshape ซึ่ง Adriaan เชื่อมโยงรวมถึง หน้าเอกสารอื่นๆ นี้ - person Cris Luengo; 09.04.2019
comment
คุณสามารถสร้างอาร์เรย์ที่มีขนาดใหญ่มาก และจับเวลาว่าต้องใช้เวลานานเท่าใดในการปรับรูปร่างใหม่ และใช้เวลานานเท่าใดในทรานสโพส คุณจะเห็นว่า reshape เป็นเรื่องเล็กน้อย ไม่มีการคัดลอกข้อมูล และการขนย้ายใช้เวลาในระยะเวลาอันไม่สำคัญ โดยจะทำการคัดลอกข้อมูล - person Cris Luengo; 09.04.2019

ตามเอกสารของ Python 1,2 มันแค่ทำให้ array (ดังนั้นทำให้เป็นเวกเตอร์ 1-D เชิงเส้น จากนั้นใช้การจัดทำดัชนี มันจะถูกส่งกลับไปยังอาร์เรย์ใหม่ของขนาดที่กำหนด ตัวอย่างเช่น:

start_array = 
[1,2,3,4;
5,6,7,8;
9,10,11,12]

i_a = [1,2,3,4,5,6,7,8,9,10,11,12] %implicit, not visible for user

result_array = 
[i_a(1), i_a(6), i_a(11); 
i_a(5), i_a(10), i_a(4); 
i_a(9), i_a(3), i_a(8); 
i_a(2), i_a(7), i_a(12)]
person Karls    schedule 08.04.2019
comment
ตอนนี้คุณถือว่าองค์ประกอบของคุณเป็นแถวหลัก ไม่ใช่ แต่จะถูกเก็บไว้ (อย่างน้อยใน MATLAB ซึ่งไวยากรณ์ที่คุณใช้) ตามลำดับคอลัมน์หลัก - person Adriaan; 08.04.2019
comment
ลำดับแถวหรือคอลัมน์ไม่เกี่ยวข้องที่นี่ แต่แสดงเฉพาะแนวคิดเท่านั้น ฉันใช้เอกสาร Python SciPy อย่างเป็นทางการใน MATLAB สามารถทำได้ด้วยวิธีอื่น - person Karls; 08.04.2019
comment
ภายใต้ประทุน อาร์เรย์จำนวนมากจะเหมือนกับ MATLABs, 1D เสมอ เพียงเปลี่ยนวิธีการแปลดัชนี 2D (ในกรณีนี้) ไปเป็นอาร์เรย์ 1D นั้น และวิธีการแสดงดัชนี - person Ander Biguri; 09.04.2019
comment
อ้างอิงจากเอกสารประกอบ You can think of reshaping as first raveling the array [...] then inserting [...] using the same kind of index ดังนั้นหากพวกมันเป็นแบบเก็บถาวรเชิงเส้น มันฟังดูเหมือนเป็นเรื่องเล็กน้อย - person Karls; 09.04.2019

เมทริกซ์ที่ง่ายที่สุดที่คุณสามารถปรับรูปร่างได้คือ 2x2 แต่คุณจะเข้าใจแนวคิดนี้ (ขออภัย StackOverflow จะไม่อนุญาตให้ฉันแทรกรูปภาพหรือ LaTex ดังนั้น คุณจะต้องทนทุกข์ทรมานเล็กน้อยในการอ่านข้อความนี้)

เราเริ่มต้นด้วย A=[[a,b],[c,d]] และเราต้องการปรับรูปร่างให้เป็นอาร์เรย์ 1x4: [[a,b,c,d]] คุณสามารถทำได้โดยใช้พีชคณิต:

[[1,0]] * A * [[1,0,0,0],[0,0,0,0]] + 
[[1,0]] * A * [[0,0,0,0],[0,1,0,0]] + 
[[0,1]] * A * [[0,0,1,0],[0,0,0,0]] + 
[[0,1]] * A * [[0,0,0,0],[0,0,0,1]]

* หมายถึงการคูณเมทริกซ์

ทุกเทอมเป็นผลคูณของเมทริกซ์ที่สอดคล้อง: 1x2 * 2x2 * 2x4 ซึ่งให้ผลลัพธ์เป็นรูปร่าง 1x4

เทอมที่ 1 ให้คุณ [[a,0,0,0]], [[0,b,0,0]] ที่ 2, [[0,0,c,0]] ที่ 3 และเทอมที่ 4 [[0,0,0,d]]

การสรุปสิ่งนี้โดยพลการของรูปร่าง nxm ไม่ควรยากเกินไป คุณจะต้องมีเทอม n*m แทนที่จะเป็น 4 เนื่องจากเมทริกซ์ที่ปรับรูปร่างใหม่ของคุณจะเป็น 1x(n*m) แต่ละเทอมจะต้องสอดคล้องกัน ดังนั้น คุณจะต้องมีเมทริกซ์ที่มีรูปร่าง 1xn เพื่อตี A จากด้านซ้าย และเมทริกซ์ที่มีรูปร่าง mx(n*m) เพื่อตี A จากด้านขวา

หากคุณต้องการปรับรูปร่าง A ของรูปร่าง nxm ให้เป็นรูปร่าง kxl โดยที่ k*l=n*m คุณจะต้องตี A จากด้านซ้ายด้วยเมทริกซ์ kxn และจากด้านขวาด้วยเมทริกซ์ mx(k*l)

person gc1o1    schedule 21.04.2021