उन सभी के माध्यम से लूपिंग के बिना या किसी भी लंघन के बिना कौन सी टाइलें एक पंक्ति द्वारा प्रतिच्छेद की जाती हैं


10

मैं कुछ दिनों से इस समस्या को देख रहा हूं। मैंने इस ग्राफिक को इस मुद्दे की कल्पना करने में मदद करने के लिए धांधली की: यहाँ छवि विवरण दर्ज करें (ग्राफ से, हम जानते हैं कि रेखा 1 [, 1], [1, 2], [2, 2], [2, 3] को समाप्त करती है [ 3,3])

मैं प्रत्येक ग्रिड स्थान पर लाइन के साथ कदम रखना चाहता हूं और यह देखना चाहता हूं कि ग्रिड स्थान की सामग्री ठोस है या नहीं। मुझे लगता है कि मैं पहले से ही गणित को शामिल करना जानता हूं, लेकिन मैं इसे अभी तक एक साथ स्ट्रिंग करने में सक्षम नहीं हूं। मैं अपने पथफाइंडिंग एल्गोरिदम के माध्यम से एक पथ मिलने के बाद दृष्टि की परीक्षण रेखा और नोड्स को समाप्त करने के लिए इसका उपयोग कर रहा हूं - मेरे एजेंट कठबोली को एक ठोस ब्लॉक के माध्यम से देखते हैं, इसलिए वे एक के माध्यम से चलते हैं, इसलिए नोड को रास्ते से समाप्त नहीं किया जाता है क्योंकि यह एक कोने नेविगेट करने के लिए आवश्यक है।

तो, मुझे एक एल्गोरिथ्म की आवश्यकता है जो प्रत्येक ग्रिड स्थान पर लाइन के साथ कदम रखेगा जो इसे प्रतिच्छेद करता है। कोई विचार?

मैंने बहुत सारे सामान्य एल्गोरिदम पर एक नज़र डाली है, जैसे कि ब्रेसेनहैम, और एक जो लाइन के साथ पूर्वनिर्धारित अंतराल पर कदम रखता है (दुर्भाग्य से, यह विधि टाइलों को छोड़ देती है यदि वे स्टेप साइज की तुलना में छोटे कील के साथ प्रतिच्छेद कर रहे हैं)।

मैं अपने व्हाइटबोर्ड को अब फर्श () और छत () फ़ंक्शन के द्रव्यमान के साथ आबाद कर रहा हूं - लेकिन इसकी अत्यधिक जटिल हो रही है और मुझे डर है कि यह मंदी का कारण बन सकता है।


आप पहले से ही जानते हैं कि वास्तविक लाइन-बॉक्स चौराहे का परीक्षण कैसे करें, है ना? बस पूछें, इसका कारण उत्तर के लिए प्रासंगिक है।
ट्रैविसग

डुप्लिकेट के संभावित डुप्लिकेट मैं फ्लोटिंग-पॉइंट एंडपॉइंट्स के लिए ब्रेसेनहैम की लाइन एल्गोरिदम को कैसे सामान्य कर सकता हूं? (सवाल वास्तव में ब्रेसेनहैम के बारे में नहीं है)
सैम होसेवर

जवाबों:


6

यदि आप ब्लॉकिंग को जानते हैं (आप बिंदु X को जानते हैं और आप ब्लॉक सूची में ब्लॉक [0,1] को शामिल नहीं करते हैं, तो मुझे लगता है कि आपको पता है कि शुरुआती ब्लॉक भी है), मुझे लगता है कि आपको निश्चित रूप से ब्रेसेनहैम के एल्गोरिथ्म का उपयोग करना चाहिए। आपने लिखा, आपने इसे देखा।

यह इस समस्या के लिए उपयुक्त एल्गोरिथम है। यह एक तरह से लिखा जा सकता है, यह केवल पूर्णांकों के साथ गणना करता है। आप वेब पर बहुत सारे कार्यान्वयन पा सकते हैं।

संपादित करें:

मुझे क्षमा करें, मुझे यह महसूस नहीं हुआ है कि ब्रेसेनहम सभी ब्लॉक नहीं पाएंगे। इसलिए मुझे बेहतर समाधान मिला । C ++ में भी कोड लिखा है, लेकिन मुझे लगता है कि इसे समझना मुश्किल नहीं होना चाहिए :)


1
ब्रेशेनहैम एल्गोरिथ्म के अतीत को देखने का कारण विशुद्ध रूप से विकिपीडिया पर छवि के कारण था। ( en.wikipedia.org/wiki/File:Bresenham.svg ) आप देख सकते हैं कि रेखा कुछ अनचाहे वर्गों को स्वीकार करती है, यद्यपि बमुश्किल। मुझे कुछ ऐसा चाहिए जो हर टाइल का पता लगाएगा , चाहे वह कितना भी छोटा टुकड़ा क्यों न हो। संपादित करें: ऐसा प्रतीत होता है कि मुझे ब्रेसेनहैम की वैसे भी गलतफहमी है। मुझे इसे उलटने की ज़रूरत है - मेरे पास पहला और आखिरी बिंदु है, और मुझे उन टाइलों की ज़रूरत है जो इसे प्रतिच्छेदन करती हैं - बजाय उस रेखा के जो कि सबसे अच्छा होगा प्लॉट करना।
बीर

@JustSuds: पोस्ट में अद्यतन के लिए जाँच करें।
zacharmarz

अरे, अरे! यह लगभग सीधे मेरे व्हाईटबोर्ड पर मेल खाता है! धन्यवाद, मेरा सिस्टम अब लागू हो गया है और काम कर रहा है। :-)
बीर

क्या आप ब्रेसेनहैम के एल्गोरिथ्म के बारे में भाग को हटा सकते हैं क्योंकि यह प्रश्न का उत्तर नहीं देता है? चिंता न करें, यह आपके उत्तर के संपादित इतिहास में रहेगा।
zenith

1

उदाहरण में कोड जिसे स्वीकृत उत्तर लिंक पूरी तरह से विकर्ण लाइनों के लिए कुछ समायोजन की आवश्यकता है। यहाँ एक पूर्ण डेमो अनुप्रयोग Qt (C ++ और QML) के साथ लिखा गया है।

ग्रिड लाइन चौराहा

प्रासंगिक C ++ कोड:

void rayCast()
{
    if (!isComponentComplete())
        return;

    mTiles.clear();
    mTiles.fill(QColor::fromRgb(255, 222, 173), mSizeInTiles.width() * mSizeInTiles.height());

    const QPoint startTile = startTilePos();
    const QPoint endTile = endTilePos();
    // http://playtechs.blogspot.com/2007/03/raytracing-on-grid.html
    int x0 = startTile.x();
    int y0 = startTile.y();
    int x1 = endTile.x();
    int y1 = endTile.y();

    int dx = abs(x1 - x0);
    int dy = abs(y1 - y0);
    int x = x0;
    int y = y0;
    int n = 1 + dx + dy;
    int x_inc = (x1 > x0) ? 1 : -1;
    int y_inc = (y1 > y0) ? 1 : -1;
    int error = dx - dy;
    dx *= 2;
    dy *= 2;

    for (; n > 0; --n)
    {
        visit(x, y);

        if (error > 0)
        {
            x += x_inc;
            error -= dy;
        }
        else if (error < 0)
        {
            y += y_inc;
            error += dx;
        }
        else if (error == 0) {
            // Ensure that perfectly diagonal lines don't take up more tiles than necessary.
            // http://playtechs.blogspot.com/2007/03/raytracing-on-grid.html?showComment=1281448902099#c3785285092830049685
            x += x_inc;
            y += y_inc;
            error -= dy;
            error += dx;
            --n;
        }
    }

    update();
}
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.