أكثر

استخدام PyShp لتحويل المضلعات في * .csv إلى ملفات * .shp؟


أقوم بتحويل بيانات csv إلى ملفات أشكال باستخدام مكتبة pyshp python. ما أريد القيام به مشابه جدًا لاستخدام pyshp لتحويل ملف .csv إلى .shp؟ ، باستثناء أنني لا أعرف كيفية التعامل مع المضلعات.

بياناتي موجودة في ملف csv. يتوافق كل صف مع مستطيل مُسمى ، أي سلسلة وإحداثيات خطوط الطول أو العرض لكل جانب من جوانب المستطيل: الجانب الأيسر (xl) ، والجانب الأيمن (xr) ، والجزء العلوي (yt) ، والجزء السفلي (yb).

لذلك تبدو بياناتي كما يلي:

name، xl، xr، yt، yb بعض الاسم ، -25.3125،22.5،47.517193،31.353634 اسم آخر ، -103.359375 ، -0.703125،80.87282،74.40216 ...

ورمز الثعبان الخاص بي بسيط جدًا. تم تعديله بشكل طفيف فقط من مثال النقاط. ولكن عندما أحاول استيراد هذه البيانات إلى خرائط جوجل ، فإن لها بعض الأخطاء في تحليلها. لذلك أعتقد أنني أفعل شيئًا خاطئًا ، لكني لست متأكدًا من ماذا؟

# إعداد قوائم فارغة لاسم البيانات ، polyPart = [] ، [] # بيانات مقروءة من ملف csv وتخزينها في قوائم مفتوحة (in_file، 'rb') كـ csvfile: r = csv.reader (csvfile، delimiter = "، ") بالنسبة لـ i ، الصف في التعداد (r): إذا كان i> 0: #skip header # تحليل البيانات في مصفوفة نقطية تمثل المربع المحيط xl = float (row [1]) xr = float (row [2]) yt = float (row [3]) yb = float (row [4]) tl = [xl، yt] tr = [xr، yt] br = [xr، yb] bl = [xl، yb] parr = [tl، tr، br، bl، tl] # مصفوفة من "جزء" واحد ، الجزء عبارة عن مصفوفة من النقاط polyPart.append ([parr]) name.append (row [0]) #Set up shapefile manager وأنشئ حقول فارغة maxStringLength = 50 w = shp.Writer (shp.POLYGON) w.field ('name'، 'C'، maxStringLength) # loop عبر البيانات واكتب ملف الشكل لـ j ، الاسم في تعداد (الاسم): w.poly (الأجزاء = polyPart [j]) w.record (الاسم) # حفظ ملف الشكل w.save (out_file)

نهجك جيد ، ولكن يمكنك جعل الأمور أكثر وضوحًا باستخدام القواميس بدلاً من القائمة وتسمح وحدة csv بذلك.
علاوة على ذلك ، يستخدم البرنامج النصي حلقتين بينما من الممكن التبسيط باستخدام حلقة واحدة فقط (الحلقة الثانية زائدة عن الحاجة ، سطر واحد من ملف csv = سجل واحد من ملف الشكل)

1) مع القواميس:

قراءة ملف csv:

مع open ('your.csv'، 'rb') مثل f: reader = csv.DictReader (f) للصف في القارئ: صف الطباعة {'xr': '22 .5 '،' yb ': '31 .353634'، 'الاسم ':' Some Name '،' xl ':' -25.3125 '،' yt ': '47 .517193'} {'xr': '-0.703125'، 'yb': '74 .40216 '،' name ':' another Name ' ، 'xl': '-103.359375'، 'yt': '80 .87282 '}

يمكنك الآن استخدام الصف ['xr'] أو الصف ['name'] بدلاً من الصف [n] (أكثر وضوحًا)

لذلك يصبح النص الخاص بك:

استيراد csv polyName، polyPart = []، [] مفتوح ('your.csv'، 'rb') كـ f: reader = csv.DictReader (f) للصف في القارئ: bl = [float (row ['xl' ])، float (row ['yb'])] tl = [float (row ['xl'])، float (row ['yt'])] br = [float (row ['xr'])، float (row ['yb'])] tr = [float (row ['xr'])، float (row ['yt'])] parr = [tl، tr، br، bl، tl] polyName.append (row ['name']) polyPart.append (parr)

كتابة ملف شكل المضلع

إذا نظرت إلى PyShpDocs ، يمكنك رؤية ما يلي:

يتم تعريف المضلع من خلال:

w = shapefile.Writer (shapefile.POLYGON) w.line (الأجزاء = [[1،5] ، [5،5] ، [5،1] ، [3،3] ، [1،1]])

والسيناريو كما كتبته هو:

import shapefile # إنشاء ملف الشكل Polygon w = shapefile.Writer (shapefile.POLYGON) # الحقل w.field ('name'، 'C'، maxStringLength) # اكتب المضلعات في ملف الشكل للجزء ، الاسم في الرمز البريدي (polyPart ، polyName): w.poly (parts = [part]) w.record (الاسم) # احفظ ملف الأشكال w.save ('your.shp')

2) الحل النهائي باستخدام حلقة واحدة فقط

لكن الحلقة الثانية ليست ضرورية هنا: يمكنك القيام بكل ذلك بحلقة واحدة (قراءة ملف csv وكتابة ملف الشكل دون استخدام قوائم polyName و polyPart).

w = shapefile.Writer (shapefile.POLYGON) w.field ('name'، 'C'، 50) مع open ('your.csv'، 'rb') كـ f: reader = csv.DictReader (f) للصف في القارئ: bl = [float (row ['xl'])، float (row ['yb'])] tl = [float (row ['xl'])، float (row ['yt'])] br = [float (row ['xr'])، float (row ['yb'])] tr = [float (row ['xr'])، float (row ['yt'])] parr = [tl، tr، br، bl، tl] w.poly (parts = [parr]) w.record (row ['name']) w.save ("your.shp")

النتيجة في QGIS:


ليس من الممارسات الجيدة في الترميز تعيين متغير المكرر في حلقة for على نفس اسم القائمة التي تقوم بالتكرار عليها. يجب عليك تغيير واحد مناسمالمتغيرات.

قمت بتشغيل الكود الخاص بك على جهازي باستخدام مجموعة البيانات الصغيرة الخاصة بك وقام بإنشاء ملف الأشكال بشكل صحيح. أنا قادر على عرضها في ArcMap ، إلى جانب جدول البيانات الجدولية. بالطبع ، لا يوجد مرجع مكاني مرتبط بهذه البيانات ، لذلك من المحتمل أن ترغب في تحديد واحد ، كما هو موضح هنا. سأقوم بالتأكيد بتنفيذ هذا قبل المضي قدمًا.

على أي حال ، قد تجد أنه من الأسهل التعامل مع هذا. أنا (آمل) قمت بتبسيط بعض الأشياء:

استيراد ملف شكل كـ shp import csv in_file = "C: /users/paul/desktop/test.csv" out_file = "C: /users/paul/desktop/test.shp" # إعداد قوائم فارغة لبيانات polyPart = [ ]، [] # قراءة البيانات من ملف csv وتخزينها في قوائم مفتوحة (in_file، 'rb') مثل csvfile: r = csv.reader (csvfile، delimiter = "،") #Automagically skip header. التالي (ص ، لا شيء) للصف في r: # تحليل البيانات في مصفوفة نقطية تمثل المربع المحيط xl = float (row [1]) xr = float (row [2]) yt = float (row [3]) yb = float (row [4]) tl = [xl، yt] tr = [xr، yt] br = [xr، yb] bl = [xl، yb] parr = [tl، tr، br، bl، tl] # مصفوفة من "جزء" واحد ، الجزء عبارة عن مصفوفة من النقاط polyPart.append ([parr]) polyName.append (صف [0]) # إعداد كاتب ملف الأشكال وإنشاء حقول فارغة maxStringLength = 50 w = shp.Writer (shp .POLYGON) w.field ('name'، 'C'، maxStringLength) # loop عبر البيانات واكتب ملف الشكل للجزء ، الاسم في zip (polyPart ، polyName): w.poly (parts = part) w.record ( name) # حفظ الشكل w.save (out_file)

يمكنك القيام بذلك في بضعة أسطر باستخدام رشيق و GeoPandas (الذي يستخدم Fiona تحت الغطاء لملف i / o). يمكنك استخدامجميل. الهندسة. مربعلإنشاء المستطيلات ، قم بتحويلها إلى ملفGeoDataFrame، واستخدم ملفإلى ملفطريقة الحفظ كملف شكل:

من الباندا استيراد DataFrame من geopandas استيراد GeoDataFrame من بيانات مربع استيراد shapely.geometry = مربعات DataFrame.from_csv ('rect.csv') = [box (row ['xl'] ، row ['yb'] ، row ['xr' ] ، صف ['yt']) للمفتاح ، صف في data.iterrows ()] df = GeoDataFrame (مربعات ، أعمدة = ['geometry'] ، index = data.index) df.to_file ('out.shp' ، سائق = "ESRI Shapefile")

ها هو الكود المكتوب مع استيراد ملف الشكل كل سطر تم التعليق عليه جيدًا لكتابة الكود بطريقة فعالة. يكتب ملف الشكل مع الإسقاط.

استيراد ملف أشكال استيراد csv استيراد ast # قراءة csv مع فتح (r "Sample_Data.csv" ، ترميز = "utf8") كملف csv: # ديكت إنشاء ديكت ريدير = csv.DictReader (csvfile) # إنشاء ملف شكل قابل للكتابة w = ملف الشكل.الكاتب (' Sample_Data.shp ') # إنشاء سمة w.field (' id '،' C ') w.field (' nieghborho '،' C ') w.field (' plan_no '،' C ') # صف من div للصف فيictReader: # اكتب سمة الصف w.record (row ['id'] ، row ['nieghborhood'] ، row ['plan_no']) # write geom w.poly ([ast.literal_eval (row ['geom'] )]) # create prj file prj = open ("Sample_Data.prj"، "w") epsg = 'GEOGCS ["WGS 84"،' epsg + = 'DATUM ["WGS_1984"،' epsg + = 'SPHEROID [" WGS 84 "، 6378137،298.257223563]] 'epsg + ='، PRIMEM [" Greenwich "، 0]، 'epsg + =' UNIT [" degree "، 0.0174532925199433]] '# save prj file prj.write (epsg) # إغلاق فوق ملف الشكل w.close ()


شاهد الفيديو: Spatial Python 1 5 convert CSV to shape SHP using GDAL OGR (شهر اكتوبر 2021).