วิธีที่แม่นยำยิ่งขึ้นในการคำนวณพื้นที่แรสเตอร์


11

ในงานประจำวันของฉันฉันถูกถามอย่างต่อเนื่องเพื่อคำนวณพื้นที่ของชุดข้อมูลแรสเตอร์ทั่วโลกในการประมาณการทางภูมิศาสตร์ที่ความละเอียด 30 อาร์คที่สอง ชุดข้อมูลเหล่านี้เป็นผลมาจากการดำเนินการรวม (ตัวอย่างทั่วไปคือคลาสพืชรวมกับเลเยอร์ประเทศ) ในการทำเช่นนี้หน่วยของเราสร้างชุดข้อมูลแรสเตอร์ด้วยพื้นที่ของแต่ละพิกเซลในการฉายภาพทางภูมิศาสตร์ที่ 30 อาร์ควินาที ด้วยตารางพื้นที่นี้ zonalstat จะดำเนินการเพื่อรวมพื้นที่สำหรับแต่ละชั้นเรียน เนื่องจากฉันไม่แน่ใจว่าสร้างกริดพื้นที่นี้ได้อย่างไรฉันมักจะสงสัยว่าวิธีนี้มีความแม่นยำมากกว่าเพียงแค่ปฏิเสธการแรสเตอร์ในการฉายภาพพื้นที่เท่ากัน (จากการทดสอบอย่างง่ายผลลัพธ์ของทั้งสองวิธีจะคล้ายกัน) ใครบ้างประสบสถานการณ์คล้ายกันหรือไม่


@radouxju ดูเหมือนว่าคุณจะแนะนำว่าคู่มือ Bugayevskiy & Snyder ฉันอ้างว่าไม่น่าเชื่อถือและไม่เป็นทางการ (ในทางตรงกันข้ามมันเป็นทั้ง - โดยเฉพาะอย่างยิ่งการพิจารณาว่าเป็นผลมาจากความร่วมมือของหน่วยงานที่ได้รับการยอมรับระดับโลกในสหรัฐอเมริกาและรัสเซีย!) พื้นฐานของความสงสัยนั้นคืออะไร? คุณจะมองหาอะไรอีก โปรดทราบว่าการคำนวณเหล่านี้มีความแม่นยำอย่างสมบูรณ์แบบ ความแม่นยำนั้นถูก จำกัด ด้วยความแม่นยำที่พารามิเตอร์ ellipsoidal ได้รับและจากความแม่นยำในการคำนวณของคุณ: ไม่สามารถแม่นยำได้สูงกว่า
whuber

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

@radouxju ขอบคุณสำหรับคำอธิบายของคุณ! ฉันไม่ได้ตระหนักถึงความโปรดปรานจนกระทั่งชั่วโมงหลังจากฉันโพสต์คำตอบ
whuber

คำตอบ:


14

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

สูตรถูกทำให้ง่ายขึ้นโดยแบ่งการคำนวณออกเป็นขั้นตอนพื้นฐาน

ก่อนระยะทางระหว่างขอบเขตตะวันออกและตะวันตก - เส้นเมอริเดียน l0 และ l1 - เป็นเศษส่วนของวงกลมทั้งวงเท่ากับq = (l1 - l0) / 360 (เมื่อวัดเส้นเมอริเดียนเป็นองศา) หรือ1 = ( l1 - l0) / (2 * pi) (เมื่อวัดเส้นเมอริเดียนเป็นเรเดียน) หาพื้นที่ของชิ้นทั้งหมดตั้งอยู่ระหว่างแนว F0 และ F1 และเพียงคูณว่าด้วยQ

ประการที่สองเราจะใช้สูตรสำหรับพื้นที่ของแนวนอนของทรงรีที่ล้อมรอบด้วยเส้นศูนย์สูตร (ที่ f0 = 0) และขนานที่ละติจูด f (= f1) พื้นที่ของชิ้นระหว่างละติจูดทั้งสองใด ๆ f0 และ f1 (นอนอยู่บนซีกโลกเดียวกัน) จะเป็นความแตกต่างระหว่างพื้นที่ขนาดใหญ่และขนาดเล็ก

ในที่สุดหากแบบจำลองนั้นเป็นทรงรีจริง ๆ (ไม่ใช่ทรงกลม) พื้นที่ของชิ้นส่วนดังกล่าวระหว่างเส้นศูนย์สูตรและเส้นขนานที่ละติจูด f ถูกกำหนดโดย

area(f) = pi * b^2 * (log(zp/zm) / (2*e) + sin(f) / (zp*zm))

โดยที่aและbเป็นความยาวของแกนหลักและแกนรองของวงรีสร้างตามลำดับ

e = sqrt(1 - (b/a)^2)

มันคือความผิดปกติและ

zm = 1 - e*sin(f); zp = 1 + e*sin(f)

(นี่คือมากง่ายกว่าการคำนวณที่มีผิวโค้งซึ่งเป็นเพียงการประมาณที่จะคล้ายคลึงกันอยู่แล้ว. โปรดทราบความคิดเห็นโดย @cffk เกี่ยวกับวิธีการคำนวณlog(zp/zm)ในทางที่สูญเสียหลีกเลี่ยงความแม่นยำที่ละติจูดต่ำ.)

รูป

area(f) เป็นพื้นที่ของชิ้นทึบแสงจากเส้นศูนย์สูตรจนถึงละติจูด f (ประมาณ 30 องศาเหนือในภาพประกอบ X และ Y เป็นแกนพิกัดแกนกลางคาร์ทีเซียนที่แสดงสำหรับการอ้างอิง

สำหรับ WGS 84 ellipsoid ให้ใช้ค่าคงที่

a = 6 378 137 meters,  b =  6 356 752.3142 meters,

entailing

e = 0.08181919084296

(สำหรับโมเดลทรงกลมที่มีa = bสูตรจะไม่มีกำหนดคุณต้องมีขีด จำกัด เป็น e -> 0 จากด้านบนซึ่งจะลดลงเป็นสูตรมาตรฐาน2 * pi * a^2 * sin(f))

ตามสูตรเหล่านี้สี่เหลี่ยมจตุรัสขนาด 30 '30' ขึ้นอยู่กับ Equator มีพื้นที่ 3077.2300079129 ตารางกิโลเมตรในขณะที่สี่เหลี่ยมจตุรัส 30 '30' แตะเสา (ซึ่งจริง ๆ แล้วเป็นรูปสามเหลี่ยม) มีพื้นที่เพียง 13.6086152 ตาราง กิโลเมตร

ตรวจสอบสูตรที่นำไปใช้กับเซลล์ทั้งหมดของ 720 โดย 360 ตารางครอบคลุมพื้นผิวโลกให้พื้นที่ผิวรวม 4 * pi * (6371.0071809) ^ 2 ตารางกิโลเมตรแสดงให้เห็นว่ารัศมี authalicของโลกควรเป็น 6371.0071809 กิโลเมตร สิ่งนี้แตกต่างจากค่า Wikipedia ในตัวเลขนัยสำคัญสุดท้ายเท่านั้น (ประมาณหนึ่งในสิบของมิลลิเมตร) (ฉันคิดว่าการคำนวณของ Wikipedia นั้นน้อย :-)

เป็นการตรวจสอบเพิ่มเติมฉันใช้เวอร์ชันของสูตรเหล่านี้ในการทำซ้ำภาคผนวก 4 และ 5 ใน Lev M. Bugayevskiy & John P. Snyder การคาดคะเนแผนที่: คู่มืออ้างอิง (Taylor & Francis, 1995) ภาคผนวก 4 แสดงความยาวส่วนโค้งของส่วนของเส้นเมอริเดียนและแนวยาว 30 นิ้วที่มอบให้เครื่องวัดที่ใกล้ที่สุด การตรวจสอบผลลัพธ์อย่างตรงจุดแสดงข้อตกลงที่สมบูรณ์แบบ จากนั้นฉันสร้างตารางขึ้นใหม่ด้วยการเพิ่มขึ้น 0.0005 ครั้งแทนที่จะเพิ่มขึ้น 0.5 ครั้งและรวมพื้นที่สี่เหลี่ยมจตุรัสตามตัวเลขโดยประมาณกับความยาวส่วนโค้งเหล่านี้ พื้นที่ทั้งหมดของทรงรีได้รับการทำซ้ำอย่างแม่นยำให้ดีขึ้นกว่าแปดร่างที่สำคัญ ภาคผนวก 5 แสดงค่าarea(f)สำหรับf = 0, 1/2, 1, ... , 90 องศาคูณด้วย 1 / (2 * pi) ค่าเหล่านี้จะมอบให้กับตารางกิโลเมตรที่ใกล้ที่สุด การตรวจสอบค่าของภาพใกล้ 0, 45 และ 90 องศาแสดงให้เห็นถึงข้อตกลงที่สมบูรณ์


สูตรที่แน่นอนนี้สามารถนำมาใช้โดยใช้พีชคณิตแรสเตอร์เริ่มต้นด้วยตารางให้ละติจูดของขีด จำกัด บนของแต่ละเซลล์และอื่น ๆ ให้ละติจูดของขีด จำกัด ล่าง แต่ละอันก็คือกริดพิกัด y (ในแต่ละกรณีคุณอาจต้องการสร้างsin(f)และจากนั้นzmและzpเป็นผลลัพธ์ระดับกลาง) ลบผลลัพธ์ทั้งสองเอาค่าสัมบูรณ์ของนั้นและคูณด้วยเศษส่วนq ที่ได้ในขั้นตอนแรก (เท่ากับ 0.5 / 360 = 1/720 สำหรับความกว้างของเซลล์ 30 ') นี่จะเป็นกริดที่ค่าประกอบด้วยค่าที่แน่นอนพื้นที่ของแต่ละเซลล์ (ขึ้นอยู่กับความแม่นยำเชิงตัวเลขของกริด) เพียงให้แน่ใจว่าได้แสดงละติจูดในรูปแบบที่คาดหวังจากฟังก์ชั่นไซน์: เครื่องคำนวณแรสเตอร์จำนวนมากจะให้พิกัดเป็นองศา แต่คาดหวังเรเดียนสำหรับฟังก์ชันตรีโกณฯ ของพวกเขา!


สำหรับบันทึกนี่คือพื้นที่ที่แน่นอนของ 30 'x 30' เซลล์บน WGS 84 ellipsoid จาก Equator ถึงขั้วโลกในช่วงเวลา 30 'ถึง 11 ตัวเลข (ตัวเลขเดียวกันกับที่ใช้สำหรับรัศมีbเล็กน้อย):

3077.2300079,3077.0019391,3076.5458145,3075.8616605,3074.9495164,3073.8094348,3072.4414813,3070.8457347,3069.0222870,3066.9712434,3064.6927222,3062.1868550,3059.4537865,3056.4936748,3053.3066912,3049.8930202,3046.2528597,3042.3864209,3038.2939285,3033.9756204,3029.4317480,3024.6625762,3019.6683833,3014.4494612,3009.0061153,3003.3386648,2997.4474422,2991.3327939,2984.9950800,2978.4346744,2971.6519646,2964.6473522,2957.4212526,2949.9740951,2942.3063230,2934.4183938,2926.3107788,2917.9839636,2909.4384482,2900.6747464,2891.6933866,2882.4949115,2873.0798782,2863.4488581,2853.6024374,2843.5412166,2833.2658109,2822.7768503,2812.0749792,2801.1608571,2790.0351582,2778.6985716,2767.1518013,2755.3955665,2743.4306011,2731.2576543,2718.8774905,2706.2908892,2693.4986451,2680.5015685,2667.3004848,2653.8962347,2640.2896746,2626.4816763,2612.4731271,2598.2649300,2583.8580035,2569.2532818,2554.4517149,2539.4542684,2524.2619238,2508.8756783,2493.2965451,2477.5255533,2461.5637477,2445.4121891,2429.0719545,2412.5441367,2395.8298444,2378.9302026,2361.8463521,2344.5794500,2327.1306692,2309.5011988,2291.6922441,2273.7050264,2255.5407830,2237.2007674,2218.6862492,2199.9985139,2181.1388633,2162.1086151,2142.9091030,2123.5416769,2104.0077025,2084.3085615,2064.4456516,2044.4203864,2024.2341953,2003.8885234,1983.3848318,1962.7245972,1941.9093120,1920.9404843,1899.8196375,1878.5483108,1857.1280585,1835.5604507,1813.8470724,1791.9895239,1769.9894206,1747.8483931,1725.5680867,1703.1501618,1680.5962932,1657.9081707,1635.0874985,1612.1359952,1589.0553936,1565.8474409,1542.5138984,1519.0565410,1495.4771578,1471.7775513,1447.9595378,1424.0249466,1399.9756206,1375.8134157,1351.5402005,1327.1578567,1302.6682785,1278.0733724,1253.3750574,1228.5752643,1203.6759360,1178.6790272,1153.5865040,1128.4003439,1103.1225355,1077.7550785,1052.2999830,1026.7592702,1001.1349711,975.42912705,949.64378940,923.78101904,897.84288636,871.83147097,845.74886152,819.59715539,793.37845851,767.09488512,740.74855748,714.34160569,687.87616739,661.35438752,634.77841811,608.15041795,581.47255240,554.74699308,527.97591765,501.16150951,474.30595754,447.41145586,420.48020351,393.51440422,366.51626611,339.48800143,312.43182627,285.34996030,258.24462644,231.11805066,203.97246162,176.81009042,149.63317034,122.44393648,95.244625564,68.037475592,40.824725575,13.608615243

ค่าอยู่ในหน่วยตารางกิโลเมตร


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

area(f) = 2 * pi * b^2 * z * (1 + (4/3)y + (6/5)y^2 + (8/7)y^3 + ...)

ที่ไหน

z = sin(f), y = (e*z)^2.

(สูตรที่เทียบเท่าปรากฏใน Bugayevskiy & Snyder, op. cit. , สมการ (2.1))

เนื่องจาก e ^ 2 มีขนาดเล็กมาก (ประมาณ 1/150 สำหรับแบบจำลองรูปไข่ทั้งหมดของโลก) และzอยู่ระหว่าง 0 และ 1, yก็เล็กเช่นกัน ดังนั้นคำศัพท์ y ^ 2, y ^ 3, ... เล็กลงอย่างรวดเร็วเพิ่มทศนิยมอีกสองตำแหน่งให้แม่นยำยิ่งขึ้นสำหรับแต่ละคำ ถ้าเราจะไม่สนใจYทั้งหมดสูตรจะเป็นที่ของพื้นที่ของรูปทรงกลมของรัศมีที่ข คำศัพท์ที่เหลือสามารถเข้าใจได้ว่าเป็นการแก้ไขเส้นศูนย์สูตรของโลก


แก้ไข

มีการตั้งคำถามบางคำถามเกี่ยวกับการคำนวณระยะทางพื้นที่ทางภูมิศาสตร์เปรียบเทียบกับสูตรที่แน่นอนเหล่านี้ วิธีระยะทางเนื้อที่ใกล้เคียงกับแต่ละจัตุรัสโดย geodesics แทนที่จะแนวที่เชื่อมต่อมุมของมันในแนวนอนและใช้สูตรแบบยุคลิดสำหรับสี่เหลี่ยมคางหมู สำหรับ quadrangles ขนาดเล็กเช่นคณะสี่คนนี้มีความเอนเอียงต่ำเล็กน้อยและมีความแม่นยำสัมพัทธ์ระหว่าง 6 และ 10 ส่วนต่อล้าน นี่เป็นพล็อตของข้อผิดพลาดสำหรับ WGS 84 (หรือรูปไข่โลกที่สมเหตุสมผลสำหรับเรื่องนั้น):

รูปที่ 2

ดังนั้นหาก (1) คุณสามารถเข้าถึงการคำนวณระยะทางมาตรวิทยาและ (2) สามารถทนต่อข้อผิดพลาดระดับ ppm คุณอาจพิจารณาใช้การคำนวณทางธรณีวิทยาเหล่านั้นและคูณผลลัพธ์ของพวกเขาด้วย 1.00000791 เพื่อแก้ไขอคติ สำหรับความแม่นยำทศนิยมสองตำแหน่งให้ลบ pi / 2 * cos (2f) / 10 ^ 6 จากปัจจัยการแก้ไข: ผลลัพธ์จะแม่นยำภายใน 0.04 ppm


1
หากระบบของคุณมีฟังก์ชัน atanh คุณสามารถผลลัพธ์ที่แม่นยำมากขึ้นเล็กน้อย (ปัดเศษรอบน้อยกว่า) แทนที่บันทึก (zp / zm) เป็น 2 * atanh (e * sin (f))
cffk

@ cffk นั่นเป็นจุดที่ดี ฉันได้รับสูตรดั้งเดิมในแง่ของ atanh แต่เปลี่ยนเป็นลอการิทึมโดยคาดหวังว่า (a) ผู้ใช้ GIS ส่วนใหญ่จะไม่คุ้นเคยกับฟังก์ชั่นนี้และ (b) ผู้ใช้จำนวนมากจะไม่สามารถเข้าถึงระบบที่มีให้ แม้ว่าการสูญเสียความแม่นยำเป็นเรื่องที่น่ากังวล แต่การตรวจสอบขนาดของความเยื้องศูนย์กลางอย่างรวดเร็วแสดงให้เห็นว่ามีการสูญเสียเพียงเล็กน้อยเมื่อทำงานกับรูปไข่ของโลก - อาจเป็นทศนิยมมากกว่าสองตำแหน่งเล็กน้อย ฉันได้จัดเตรียม power series บางส่วนเพื่อให้ผู้อ่านได้รับความแม่นยำอย่างเต็มที่หากพวกเขาต้องการ
whuber

3

คำตอบสำหรับคำถามของ radouxju ขึ้นอยู่กับรูปร่างของพิกเซลเมื่อฉายลงในวงรี หากระบบพิกัดของแรสเตอร์นั้นเป็นลองจิจูดและละติจูดแล้วพิกเซลนั้นเป็นสี่เหลี่ยมมุมฉากและสามารถใช้คำตอบของ whuber หรือโดยทั่วไปคุณสามารถใช้สูตรสำหรับรูปหลายเหลี่ยมที่มีขอบเป็นรูปสี่เหลี่ยมจัตุรัส หากระบบพิกัดเป็นเส้นโครงร่างขนาดใหญ่ (UTM, ระนาบสถานะ ฯลฯ ) จะมีความแม่นยำมากขึ้นในการประมาณขอบด้วย geodesics และใช้สูตรสำหรับรูปหลายเหลี่ยมเชิงพื้นที่ รูปหลายเหลี่ยม geodesic อาจจะดีที่สุดสำหรับการใช้งานทั่วไปเนื่องจากแตกต่างจากรูปหลายเหลี่ยมเส้น rhumb พวกเขาจะ "ประพฤติดี" ใกล้กับเสา

การดําเนินการของสูตรสำหรับเนื้อที่และรูปหลายเหลี่ยม rhumb สายที่ให้บริการโดยห้องสมุดของฉันGeographicLib พื้นที่ทางธรณีวิทยามีหลายภาษา พื้นที่บรรทัด rhumb คือ C ++ เท่านั้น มีรุ่นออนไลน์ (เนื้อที่เส้น + rhumb) สามารถใช้ได้เป็นที่นี่ ความถูกต้องของการคำนวณเหล่านี้มักจะดีกว่า 0.1 ตารางเมตร

คุณจะต้องตัดสินเรื่องความน่าเชื่อถือ / เป็นทางการ ... สูตรทางธรณีวิทยาได้มาในพื้นที่ภายใต้ความรู้ทางภูมิศาสตร์ (แดเนียลเซ่น, 1989, ต้องสมัครสมาชิก) และอัลกอริทึมสำหรับธรณีฟิสิกส์ (Karney, 2013, การเข้าถึงแบบเปิด) สูตรสาย rhumb จะได้รับที่นี่


(+1) ฉันกำลังอัปเดตโพสต์นี้สำหรับข้อมูลที่เป็นประโยชน์แม้ว่าจะไม่ได้ตอบคำถาม (หรือความโปรดปราน) ซึ่งทั้งสองอย่างนี้เกี่ยวกับ rasters ในระบบพิกัดทางภูมิศาสตร์โดยเฉพาะ
whuber

1

ฉันวิ่งข้ามคำถามนี้เมื่อพยายามกำหนดสูตรสำหรับพื้นที่ของ WGS84 พิกเซล แม้ว่าคำตอบของ @ whuber จะมีข้อมูลนี้ แต่ก็ยังมีงานบางอย่างที่จะได้รับสูตรสำหรับพื้นที่ของพิกเซลสี่เหลี่ยมจัตุรัสที่ละติจูดที่กำหนด ฉันได้รวมฟังก์ชั่น Python ที่ฉันเขียนไว้ด้านล่างแล้วสรุปสิ่งนี้ลงในการโทรครั้งเดียว แม้ว่ามันจะไม่ตอบคำถามของผู้โพสต์โดยตรงเกี่ยวกับพื้นที่ของแรสเตอร์ทั้งหมด (แม้ว่าจะมีผลรวมพื้นที่ของพิกเซลทั้งหมด) แต่ฉันคิดว่ามันยังเป็นข้อมูลที่มีประโยชน์สำหรับคนที่อาจค้นหาการคำนวณที่คล้ายกัน

def area_of_pixel(pixel_size, center_lat):
    """Calculate m^2 area of a wgs84 square pixel.

    Adapted from: https://gis.stackexchange.com/a/127327/2397

    Parameters:
        pixel_size (float): length of side of pixel in degrees.
        center_lat (float): latitude of the center of the pixel. Note this
            value +/- half the `pixel-size` must not exceed 90/-90 degrees
            latitude or an invalid area will be calculated.

    Returns:
        Area of square pixel of side length `pixel_size` centered at
        `center_lat` in m^2.

    """
    a = 6378137  # meters
    b = 6356752.3142  # meters
    e = math.sqrt(1 - (b/a)**2)
    area_list = []
    for f in [center_lat+pixel_size/2, center_lat-pixel_size/2]:
        zm = 1 - e*math.sin(math.radians(f))
        zp = 1 + e*math.sin(math.radians(f))
        area_list.append(
            math.pi * b**2 * (
                math.log(zp/zm) / (2*e) +
                math.sin(math.radians(f)) / (zp*zm)))
    return pixel_size / 360. * (area_list[0] - area_list[1])
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.