การใช้ CPU ให้เกิดประโยชน์สูงสุด


9

สคริปต์ของฉันตัดกันกับเส้นหลายเหลี่ยม เป็นกระบวนการที่ยาวนานเนื่องจากมีมากกว่า 3000 บรรทัดและมากกว่า 500,000 โพลิกอน ฉันดำเนินการจาก PyScripter:

# Import
import arcpy
import time

# Set envvironment
arcpy.env.workspace = r"E:\DensityMaps\DensityMapsTest1.gdb"
arcpy.env.overwriteOutput = True

# Set timer
from datetime import datetime
startTime = datetime.now()

# Set local variables
inFeatures = [r"E:\DensityMaps\DensityMapsTest.gdb\Grid1km_Clip", "JanuaryLines2"]
outFeatures = "JanuaryLinesIntersect"
outType = "LINE"

# Make lines
arcpy.Intersect_analysis(inFeatures, outFeatures, "", "", outType)

#Print end time
print "Finished "+str(datetime.now() - startTime)


คำถามของฉันคือ: มีวิธีที่จะทำให้ซีพียูทำงานที่ 100% หรือไม่? มันทำงานที่ 25% ตลอดเวลา ฉันเดาว่าสคริปต์จะทำงานเร็วขึ้นหากโปรเซสเซอร์อยู่ที่ 100% เดาผิด
เครื่องของฉันคือ:

  • มาตรฐาน Windows Server 2012 R2
  • หน่วยประมวลผล: Intel Xeon CPU E5-2630 0 @ 2.30 GHz 2.29 GHz
  • หน่วยความจำที่ติดตั้ง: 31,6 GB
  • ประเภทของระบบ: ระบบปฏิบัติการ 64 บิตโปรเซสเซอร์ที่ใช้ x64


ป้อนคำอธิบายรูปภาพที่นี่


ฉันอยากจะแนะนำให้ไปหลายเธรด นั่นไม่ใช่เรื่องง่ายที่จะตั้งค่า แต่จะชดเชยความพยายามมากกว่า
alok jha

1
ดัชนีเชิงพื้นที่ประเภทใดที่คุณใช้กับรูปหลายเหลี่ยมของคุณ
Kirk Kuykendall

1
คุณเคยลองใช้การทำงานแบบเดียวกันกับ ArcGIS Pro หรือไม่? เป็น 64 บิตและรองรับการทำงานแบบมัลติเธรด ฉันจะแปลกใจถ้ามันฉลาดพอที่จะแยกการแยกออกเป็นหลายเธรด แต่ควรลองดู
Kirk Kuykendall

คลาสคุณลักษณะรูปหลายเหลี่ยมมีดัชนีเชิงพื้นที่ชื่อ FDO_Shape ฉันไม่ได้คิดเรื่องนี้ ฉันควรสร้างอันใหม่หรือไม่? มันยังไม่เพียงพอหรือ
Manuel Frias

1
เนื่องจากคุณมี RAM จำนวนมาก ... คุณลองคัดลอกรูปหลายเหลี่ยมลงในคุณลักษณะหน่วยความจำในหน่วยความจำแล้วตัดกับบรรทัดนั้นหรือไม่ หรือถ้าเก็บไว้ในดิสก์คุณลองอัดมันหรือไม่? การกระชับกะทัดรัดควรปรับปรุง i / o
Kirk Kuykendall

คำตอบ:


13

ให้ฉันเดา: cpu ของคุณมี 4 คอร์ดังนั้นการใช้งาน cpu 25% คือการใช้งาน 100% ของหนึ่งคอร์และ 3 คอร์ที่ไม่ได้ใช้งาน

ทางออกเดียวคือทำให้โค้ดมีหลายเธรด แต่นั่นไม่ใช่งานง่าย


4
CPU เขากล่าวใช้ 6 แกนและ 12 กระทู้
Kersten

5
สวัสดีฉันไม่สามารถลงคะแนนได้ แต่ฉันต้องการ! Python มี GIL แต่น่าเสียดายที่คุณไม่สามารถมัลติเธรดได้เลย (สิ่งที่ดีที่สุดที่คุณสามารถทำได้คือให้ GIL ปลดล็อกเมื่อบล็อกเธรดบน syscall)
Alec Teal

2
@AlecTeal คุณสามารถทำได้แน่นอนเช่น Jython หรือmultiprocessingโมดูล
rightfold

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

@AlecTeal มัน spawns กระบวนการ (ซึ่งเป็นวิธีหนึ่งที่จะทำขนาน) ดูเอกสารประกอบของmultiprocessingโมดูล
rightfold

13

ฉันไม่แน่ใจว่านี่เป็นภาระผูกพันของ CPU ฉันคิดว่ามันจะเป็นการดำเนินการ I / O-bound ดังนั้นฉันจึงต้องการใช้ดิสก์ที่เร็วที่สุดที่ฉันเข้าถึงได้

หาก E: เป็นไดรฟ์เครือข่ายให้กำจัดขั้นตอนแรก หากไม่ใช่ดิสก์ประสิทธิภาพสูง (<7ms ค้นหา) แสดงว่าเป็นวินาที คุณอาจได้รับประโยชน์จากการคัดลอกเลเยอร์หลายเหลี่ยมไปยังin_memoryเวิร์กสเปซ แต่ข้อดีอาจขึ้นอยู่กับขนาดของคลาสฟีเจอร์รูปหลายเหลี่ยมและไม่ว่าคุณจะใช้การประมวลผลพื้นหลัง 64 บิตหรือไม่

การเพิ่มประสิทธิภาพการรับส่งข้อมูล I / O มักเป็นกุญแจสำคัญในประสิทธิภาพของ GIS ดังนั้นฉันขอแนะนำให้คุณให้ความสนใจน้อยลงกับ CPU meter และให้ความสนใจกับเครือข่ายและดิสก์เมตรมากขึ้น


4

ฉันมีปัญหาคล้ายกันเกี่ยวกับประสิทธิภาพการทำงานของสคริปต์ arcpy ปัญหาคอขวดที่สำคัญไม่ใช่ CPU เป็นฮาร์ดไดรฟ์หากคุณใช้ข้อมูลจากเครือข่ายซึ่งเป็นสถานการณ์ที่เลวร้ายที่สุดพยายามย้ายข้อมูลของคุณไปยังไดรฟ์ SSD จากนั้นเปิดสคริปต์ของคุณจากบรรทัดคำสั่ง ไม่ใช่จาก pyscripter, pyscripter ช้าลงเล็กน้อยอาจเป็นเพราะมันมีบางสิ่งที่ดีบั๊กถ้าคุณไม่พอใจลองคิดถึงสคริปต์ของคุณเพราะแต่ละไพ ธ อนใช้ซีพียูแต่ละคอร์ CPU ของคุณมี 6 คอร์ดังนั้นคุณสามารถเปิดได้ 6 สคริปต์พร้อมกัน


3

ในขณะที่คุณใช้งานไพ ธ อนและตามที่แนะนำข้างต้นให้พิจารณาใช้มัลติโปรเซสเซอร์หากปัญหาของคุณสามารถทำงานแบบขนานได้

ฉันเขียนบทความเล็ก ๆ บนเว็บไซต์ geonet เกี่ยวกับการแปลงสคริปต์ python เป็นเครื่องมือสคริปต์ python ที่สามารถใช้ภายใน modelbuilder เอกสารแสดงรหัสและอธิบายถึงข้อผิดพลาดบางประการสำหรับการเรียกใช้เป็นเครื่องมือสคริปต์ นี่เป็นเพียงที่เดียวที่จะเริ่มมองหา:

https://geonet.esri.com/docs/DOC-3824


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

3

ที่กล่าวก่อนที่คุณควรใช้multiprocessingหรือเกลียว แต่ที่นี่ข้อแม้มา: ปัญหาจะต้องหาร! ดังนั้นมีลักษณะที่https://en.wikipedia.org/wiki/Divide_and_conquer_algorithms

หากปัญหาของคุณหารได้คุณจะต้องดำเนินการดังนี้:

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

แต่อย่างที่ geogeek ได้กล่าวมามันอาจไม่ใช่ปัญหาการ จำกัด CPU แต่เป็นปัญหา IO หากคุณมี RAM เพียงพอคุณสามารถโหลดข้อมูลทั้งหมดล่วงหน้าแล้วประมวลผลได้ซึ่งมีข้อได้เปรียบที่ข้อมูลสามารถอ่านได้ในครั้งเดียวจึงไม่ขัดขวางกระบวนการคำนวณเสมอ


3

ฉันตัดสินใจทดสอบโดยใช้ 21513 บรรทัดและ 498596 รูปหลายเหลี่ยม ฉันทดสอบวิธีมัลติโปรเซสเซอร์ (โปรเซสเซอร์ 12 ตัวในเครื่องของฉัน) โดยใช้สคริปต์นี้:

import arcpy,os
import multiprocessing
import time
t0 = time.time()
arcpy.env.overwriteOutput = True
nProcessors=4
folder=r'd:\scratch'

def function(inputs):
        nGroup=inputs[0]
        pGons=inputs[1]
        lines=inputs[2]
        outFeatures = '%s%s%s_%i.shp' %(folder,os.sep,'inters',nGroup)
        fids= tuple([i for i in range(nGroup,500000,nProcessors-1)])
        lyr='layer%s'%nGroup
        query='"FID" in %s' %str(fids)
        arcpy.MakeFeatureLayer_management(pGons,lyr,query)
        arcpy.Intersect_analysis([lines,lyr], outFeatures)
        return outFeatures
if __name__ == "__main__":
        inPgons='%s%s%s' %(folder,os.sep,'parcels.shp')
        inLines='%s%s%s' %(folder,os.sep,'roads.shp')
        m,bList=0,[]
        for i in range(nProcessors):
                bList.append([i,inPgons,inLines])
        pool = multiprocessing.Pool(nProcessors-1)
        listik=pool.map(function, bList)
##      apply merge here
        print listik
        print ('%i seconds' %(time.time()-t0))

ผลลัพธ์วินาที:

  • ฮาร์ดไดรฟ์ในเครื่องปกติ - 191
  • ไดรฟ์ในท้องถิ่นที่เร็วมาก - 220
  • ไดรฟ์เครือข่าย - 252

สิ่งที่ตลกใช้เวลาเพียง 87 วินาทีโดยใช้เครื่องมือการประมวลผลจาก mxd อาจมีบางอย่างผิดปกติกับแนวทางของฉันในการรวม ...

อย่างที่เราเห็นว่าฉันใช้แบบสอบถาม FID ที่น่าเกลียดแทนใน (0, 4, 8,12 … 500000) เพื่อให้งานหารได้

เป็นไปได้ว่าแบบสอบถามที่ยึดตามเขตข้อมูลที่คำนวณล่วงหน้าเช่น CFIELD = 0 จะลดเวลาลงอย่างมาก

ฉันยังพบว่าเวลาที่รายงานโดยเครื่องมือหลายตัวประมวลผลอาจแตกต่างกันมาก


1
ใช่คุณกำลังใช้รายการซึ่งมาพร้อมกับปัญหาการล็อค ลอง multiprocessing.queue นอกจากนี้พยายามอย่าเขียนสิ่งต่าง ๆ ในกระบวนการของผู้ปฏิบัติงาน แต่สร้างคิว ouput ด้วยข้อมูลที่คุณต้องการเขียนและปล่อยให้สิ่งนี้ทำโดยกระบวนการเขียน
เบนจามิน

3

ฉันไม่คุ้นเคยกับ PyScripter แต่ถ้าได้รับการสนับสนุนจาก CPython คุณควรใช้การประมวลผลแบบมัลติโพรเซสซิงและไม่ใช้มัลติเธรดตราบใดที่ปัญหานั้นหารด้วยตัวเองได้

CPython มีGlobal ล่ามล็อคซึ่งยกเลิกออกผลประโยชน์ใด ๆ ซึ่งหลายหัวข้ออาจนำมาในกรณีของคุณ

เพื่อความมั่นใจในหัวข้ออื่น ๆ ของ python thread นั้นมีประโยชน์ แต่ไม่ใช่ในกรณีที่คุณใช้ CPU


1

คำถามของฉันคือ: มีวิธีที่จะทำให้การทำงานของ CPU ที่ 100%

เนื่องจาก CPU ของคุณมีหลายคอร์คุณจะต้องออกจากแกนประมวลผลของคุณเท่านั้น ขึ้นอยู่กับว่าคุณมีการกำหนดค่าชิป Xeon ของคุณแล้วมันจะทำงานได้ถึง 12 คอร์ (6 ฟิสิคัลและ 6 เวอร์ชวลด้วยการเปิดไฮเปอร์เธรด) แม้แต่ 64 บิต ArcGIS ก็ยังไม่สามารถใช้ประโยชน์จากสิ่งนี้ได้และนั่นอาจส่งผลให้เกิดข้อ จำกัด ของ CPU เมื่อกระบวนการเธรดเดี่ยวของคุณขยายแกนออกไปจนสุด คุณต้องมีแอพพลิเคชั่นแบบมัลติเธรดเพื่อกระจายโหลดข้ามคอร์หรือ (มากกว่านั้น) คุณสามารถลดจำนวนคอร์ที่ CPU ของคุณกำลังทำงานเพื่อเพิ่มปริมาณงาน

วิธีที่ง่ายที่สุดในการหยุดการ จำกัด CPU (และตรวจสอบให้แน่ใจว่าเป็นข้อ จำกัด ของ CPU ไม่ใช่ข้อ จำกัด ของดิสก์ i / o) คือการเปลี่ยนการตั้งค่า BIOS สำหรับ Xeon ของคุณและตั้งค่าเป็นแกนเดี่ยวขนาดใหญ่ การเพิ่มประสิทธิภาพจะมีความสำคัญ เพียงจำไว้ว่านี่เป็นการแลกเปลี่ยนความสามารถในการทำงานแบบมัลติทาสกิ้งบนพีซีของคุณได้ค่อนข้างดีดังนั้นจึงเป็นการดีที่สุดถ้าคุณมีเครื่องจักรเฉพาะสำหรับกระบวนการนี้ มันง่ายกว่าการลองมัลติโค้ดของคุณ - ฟังก์ชั่น ArcGIS Desktop ส่วนใหญ่ (ณ วันที่ 10.3.1) ไม่รองรับ


การตั้งค่าใดที่คุณควรมองหาเพื่อเปลี่ยนซีพียูของคุณให้กลายเป็น "แกนเดี่ยวขนาดใหญ่เดียว"
Alex McVittie

1
เมนูที่แน่นอนจะขึ้นอยู่กับ BIOS และชิปเฟิร์มแวร์ของคุณ แต่โดยปกติจะอยู่ในการตั้งค่าเมนู BIOS> ขั้นสูง> การกำหนดค่า CPU คุณจะต้องปิดไฮเปอร์เธรดแล้วตั้งค่าจำนวนแกนเพื่อเปิดใช้งาน 0 มักจะเป็นทั้งหมด - ตั้งค่าเป็น 1 ถ้าคุณต้องการแกนใหญ่หนึ่ง ความคิดที่ดีที่จะจดบันทึกการตั้งค่าก่อนที่คุณจะเปลี่ยนสิ่งต่าง ๆ - ฟังดูชัดเจน แต่มองข้ามได้ง่ายหากสิ่งต่าง ๆ ไม่ได้ผล
kingmi
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.