শেপলি ব্যবহার করে এক লাইন স্ট্রিংয়ে ওয়েল্ড পৃথক লাইন বিভাগগুলি


13

আমি অজগরকে শেপলি ব্যবহার করছি এবং আমাকে MultiLineStringএকগুচ্ছ Linestringঅবজেক্টের সাথে দেওয়া হচ্ছে । আমি গ্যারান্টি দিতে পারি যে সমস্ত LineStringবস্তুগুলি কেবলমাত্র 2 টি শীর্ষ কোণগুলির সাথে সরল রেখা এবং সেগুলি সমস্ত একক লাইনের অংশ (কোনও শাখা নেই)।

আমি "কানেক্ট-দ্য ডটস" এবং একটি একক তৈরি করতে চাই LineString। এর জন্য আমাকে কি পুনরাবৃত্ত weালাইয়ের পদ্ধতি লিখতে হবে বা আরও দ্রুততর কোনও উপায় আছে?

উত্তর:


20

আপনি ব্যবহার করতে পারেন shapelys 'এর ops.linemergeএই কাজ করা সম্ভব:

from shapely import geometry, ops

# create three lines
line_a = geometry.LineString([[0,0], [1,1]])
line_b = geometry.LineString([[1,1], [1,0]])
line_c = geometry.LineString([[1,0], [2,0]])

# combine them into a multi-linestring
multi_line = geometry.MultiLineString([line_a, line_b, line_c])
print(multi_line)  # prints MULTILINESTRING ((0 0, 1 1), (1 1, 2 2), (2 2, 3 3))

# you can now merge the lines
merged_line = ops.linemerge(multi_line)
print(merged_line)  # prints LINESTRING (0 0, 1 1, 2 2, 3 3)

# if your lines aren't contiguous
line_a = geometry.LineString([[0,0], [1,1]])
line_b = geometry.LineString([[1,1], [1,0]])
line_c = geometry.LineString([[2,0], [3,0]])

# combine them into a multi-linestring
multi_line = geometry.MultiLineString([line_a, line_b, line_c])
print(multi_line)  # prints MULTILINESTRING ((0 0, 1 1), (1 1, 1 0), (2 0, 3 0))

# note that it will now merge only the contiguous portions into a component of a new multi-linestring
merged_line = ops.linemerge(multi_line)
print(merged_line)  # prints MULTILINESTRING ((0 0, 1 1, 1 0), (2 0, 3 0))

আমি কীভাবে জানতে পারি কোন লাইনস্ট্রিংটি একত্রীকরণ করা হয়েছিল? আমি যেমন একটি তালিকা পেতে চাই: মার্জড = [[লাইন_এ, লাইন_ বি], [লাইন_সি]]
জেমস

আপনি আপনার স্বতন্ত্র রেখার একটি তালিকাটি লুপ করতে পারেন এবং পৃথক লাইনগুলিতে নতুন একত্রিত লাইন কিনা তা পরীক্ষা করতে পারেন contains()। যাঁরা এতে নেই তাদের একীভূত করা হত না। যেমন merged_line.contains(line_a)যা বুলিয়ান ফিরে আসবে TrueবাFalse
songololo

অনেক ধন্যবাদ. লাইনটি মার্জড_লাইনগুলিতে রয়েছে কিনা আপনি কীভাবে পরীক্ষা করবেন?
জেমস 11

1
আহ, আমি বুঝতে পারি নি "" কন্টেন্টস (লাইন_এ) "একটি পূর্ব-লিখিত ফাংশন ছিল। নিখুঁত। অনেক ধন্যবাদ !
জেমস

1
দুঃখিত, আপনাকে আবার বিরক্ত করার জন্য ... তবে আপনি কি জানেন যে "লাইনগুলি" (একে অপরের থেকে নির্দিষ্ট সর্বাধিক দূরত্বে) লাইনগুলি কে মার্জ করবেন? আমি জিজ্ঞাসা করছি কারণ আমি অনেকগুলি লাইন দেখছি যা মার্জ করা উচিত, তবে তাদের মধ্যে একটি ছোট গ্যাব থাকার কারণে সেগুলি একীভূত হয় না।
জেমস

2

আমি মনে করি আপনি এটিকে শেপলি.পস.লাইনমার্জ () পদ্ধতিটি শেপলি দিয়ে ব্যবহার করতে পারেন।

দেখে মনে হচ্ছে এটি ইনপুট হিসাবে লাইনগুলির একটি তালিকা নিতে পারে এবং তাদের মার্জ করতে পারে। আমি আগে 'বহুভুজ' পদ্ধতি ব্যবহার করেছি এবং এটি লাইনের একটি তালিকা গ্রহণ করে।

দস্তাবেজটি এখানে দেখুন: http://toblerity.org/shapely/manual.html#shapely.ops.line جهاز


1
আপনি কী জানেন যে কীভাবে "নিকটবর্তী" লাইনগুলি মার্জ করবেন (একে অপরের থেকে নির্দিষ্ট সর্বাধিক দূরত্বে)?
জেমস

বহুভুক্ত_ফুল কিছুটা ভাল কাজ করে, তবে ফলস্বরূপ আমি কিছু অদ্ভুত ডেটাস্ট্রাকচার পেয়েছি
ডানুকার

1

shapely.ops.linemerge()আমার কিছু লাইনের জন্য ব্যর্থ হয়েছে তাই আমাকে এটি ম্যানুয়ালি করতে হয়েছিল। এটি "যে" রেখাগুলি নিজেই "ফিরে" এসেছিল তা ব্যর্থ বলে মনে হচ্ছে, একই পয়েন্টটি একাধিকবার অতিক্রম করে। আমার ক্ষেত্রে, আমি জানি যে লাইনগুলি সঠিক ক্রমে রয়েছে তাই তাদের মার্জ করার জন্য একটি ছোট ফাংশন লেখা সহজ হয়েছিল।

from shapely.geometry import LineString
from typing import List


def merge_lines(lines: List[LineString]) -> LineString:
    last = None
    points = []
    for line in merged_line:
        current = line.coords[0]

        if last is None:
            points.extend(line.coords)
        else:
            if last == current:
                points.extend(line.coords[1:])
            else:
                print('Skipping to merge {} {}'.format(last, current))
                return None
        last = line.coords[-1]
    return LineString(points)

আশা করি এটি কাউকে সাহায্য করবে


0

shapely.ops.linemergeকাজ করে যদি রেখাগুলি সংহত হয় ("টিপস" উপাদান লাইনগুলির "লেজ" এর সাথে মিলে যায়), তবে যদি সেগুলি অ-সংযুক্ত থাকে (টিপস এবং লেজের মধ্যে কোনও ফাঁক থাকে) তবে এটি অন্য একটি মাল্টলাইনস্ট্রিং প্রদান করে। যদি আপনার উপাদানগুলির লাইনগুলি সুশৃঙ্খলভাবে থাকে (পরের লাইনের শুরুতে এক লাইনের সমাপ্তি থাকে) তবে টিপ-টু লেজ ফাঁক থাকলে আপনি স্থানাঙ্কগুলি বের করতে পারেন এবং সেগুলি একটি নতুন সাধারণ লাইন তৈরি করতে পারেন। এই পদ্ধতিটি আরও জটিল সাবলাইনগুলি (যেমন দুটি পয়েন্টের বেশি সহ সাবলাইনগুলি) দিয়ে তৈরি মাল্টি-লাইনের জন্যও কাজ করে।

import shapely

# Make a MultiLineString to use for the example
inlines = shapely.geometry.MultiLineString(
    [shapely.geometry.LineString([(0,0),(0,0.9)]), 
     shapely.geometry.LineString([(0,1),(1,1)])]
)

# Put the sub-line coordinates into a list of sublists
outcoords = [list(i.coords) for i in inlines]

# Flatten the list of sublists and use it to make a new line
outline = shapely.geometry.LineString([i for sublist in outcoords for i in sublist])
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.