झीलों में भरें, 2 डी


22

इस समस्या का एक आयामी संस्करण बहुत आसान था, इसलिए यहां एक कठिन 2 डी संस्करण है।

आपको मानक इनपुट पर भूमि की ऊँचाई का 2 डी सरणी दिया जाता है, और आपको यह पता लगाना होगा कि बारिश होने पर झीलें कहाँ बनेंगी। ऊंचाई का नक्शा समावेशी 0-9 की संख्या का एक आयताकार सरणी है।

8888888888
5664303498
6485322898
5675373666
7875555787

आपको एक ही सरणी का उत्पादन करना होगा, जिसमें सभी स्थानों को बदल दिया जाएगा जो पानी के नीचे होंगे *

8888888888
566*****98
6*85***898
5675*7*666
7875555787

पानी तिरछे बच सकता है, इसलिए इस विन्यास में कोई झील नहीं होगी:

888
838
388

सबसे छोटा कोड जीतता है। आपका कोड 80 चौड़े और 24 उच्च आकार का होना चाहिए।

तीन और उदाहरण:

77777    77777
75657    7*6*7
75757 => 7*7*7
77677    77677
77477    77477

599999    599999
933339    9****9
936639 => 9*66*9
935539    9*55*9
932109    9****9
999999    999999

88888888    88888888
84482288    8**8**88
84452233 => 8**5**33
84482288    8**8**88
88888888    88888888

4
यदि संभव हो तो कुछ और टेस्टकेस अच्छे होंगे, (विशेषकर इनपुट आप एक किनारे के मामले पर विचार करेंगे)।
वेंटरो

क्या उत्पादन लाइनों में अनुगामी व्हाट्सएप की अनुमति है?
हॉलवबो

@ पहलवबो: नहीं। आपको क्यों चाहिए होगा?
कीथ रान्डेल

कीथ: मेरे पास एक और समाधान था जहां मैंने इनपुट लाइनों को एक निश्चित चौड़ाई में गद्देदार किया, और एल्गोरिथ्म में कुछ बाइट्स को बचाया। अगर मुझे आउटपुट के लिए पैडिंग को हटाना है, तो यह दृष्टिकोण मेरे वर्तमान में सबसे अच्छा समाधान की तुलना में अधिक बाइट्स लेता है।
हॉल्वैबो

जवाबों:


7

हास्केल, 258 अक्षर

a§b|a<b='*'|1<3=a
z=[-1..1]
l m=zipWith(§)m$(iterate(b.q)$b(\_ _->'9'))!!(w*h)where
 w=length m`div`h
 h=length$lines m
 q d i=max$minimum[d!!(i+x+w*y)|x<-z,y<-z]
 b f=zipWith(\n->n`divMod`w¶f n)[0..]m
 (j,i)¶g|0<i&&i<w-2&&0<j&&j<h-1=g|1<3=id
main=interact l

उदाहरण रन:

$> runhaskell 2638-Lakes2D.hs <<TEST
> 8888888888
> 5664303498
> 6485322898
> 5675373666
> 7875555787
> TEST
8888888888
566*****98
6*85***898
5675*7*666
7875555787

सभी यूनिट टेस्ट पास करता है। आकार पर कोई मनमानी सीमा नहीं।


  • संपादित करें (281 → 258): स्थिरता के लिए परीक्षण न करें, बस ऊपरी सीमा पर पुनरावृति; निरंतर तर्क पारित करना बंद करोm

5

पायथन, 483 491 वर्ण

a=dict()
def s(n,x,y,R):
 R.add((x,y))
 r=range(-1,2)
 m=set([(x+i,y+j)for i in r for j in r if(i,j)!=(0,0)and(x+i,y+j)not in R])
 z=m-set(a.keys())
 if len(z)>0:return 1
 else:return sum(s(n,k[0],k[1],R)for k in[d for d in m-z if a[(d[0],d[1])]<=n])
i=[list(x)for x in input().strip().split('\n')]
h=len(i)
w=len(i[0])
e=range(0,w)
j=range(0,h)
for c in[(x,y)for x in e for y in j]:a[c]=int(i[c[1]][c[0]])
for y in j:print(''.join([('*',str(a[(x,y)]))[s(a[(x,y)],x,y,set())>0] for x in e]))

मुझे पूरा यकीन है कि ऐसा करने का एक बेहतर (और छोटा) तरीका है


ज्यादातर काम करता है, लेकिन मैं बदलने के लिए किया था input()के साथ sys.stdin.read()और पीछे हटाने \nमेरी नमूना आदानों से।
कीथ रान्डेल

@ कीथ रान्डेल - sys.stdin.read()एक फ़ाइल से पढ़ना सही है? मैं अभी भी अजगर पर नया हूँ।
सिस्टम डाउन

sys.stdin.read()EOF तक STANDard INput पढ़ता है। input()मानक इनपुट की एक पंक्ति पढ़ता है और उसका मूल्यांकन करता है।
कीथ रान्डेल

4

अजगर, 478 471 वर्ण

(टिप्पणियों सहित नहीं। 452 450 वर्ण आयात में शामिल नहीं हैं।)

import sys,itertools
i=[list(x)for x in sys.stdin.read().strip().split('\n')]
h=len(i)
w=len(i[0])
n=h*w
b=n+1
e=range(h)
d=range(w)
# j is, at first, the adjancency matrix of the graph.
# The last vertex in j is the "drain" vertex.
j=[[[b,1][(t-r)**2+(v-c)**2<=1 and i[r][c]>=i[t][v]] for t in e for v in d]+[[b,1][max([r==0,r>h-2,c==0,c>w-2])]]for r in e for c in d]+[[0]*b]
r=range(b)
for k,l,m in itertools.product(r,repeat=3):
    # This is the Floyd-Warshall algorithm
    if j[l][k]+j[k][m]<j[l][m]:
        j[l][m]=j[l][k]+j[k][m]
# j is now the distance matrix for the graph.
for k in r:
    if j[k][-1]>n:
        # This means that vertex k is not connected to the "drain" vertex, and is therefore flooded.
        i[k/w][k-w*(k/w)]='*'
for r in e:print(''.join(i[r]))

यहां विचार यह है कि मैं एक निर्देशित ग्राफ का निर्माण करता हूं जहां प्रत्येक ग्रिड सेल का अपना स्वयं का शीर्ष (प्लस एक अतिरिक्त "नाली" शीर्ष) होता है। प्रत्येक उच्च मूल्यवान सेल से उसके पड़ोसी निचले मूल्यवान कोशिकाओं तक ग्राफ में एक बढ़त है, साथ ही सभी बाहरी कोशिकाओं से "नाली" शीर्ष तक एक बढ़त है। फिर मैं फ्लोयड-वारशॉल का उपयोग करके गणना करता हूं कि कौन से कोने "नाली" के शीर्ष से जुड़े हैं; किसी भी कोने जो जुड़े नहीं हैं वे बाढ़ आएंगे और एक तारांकन चिह्न के साथ खींचे जाएंगे।

मुझे पायथन कोड को संघनित करने का अधिक अनुभव नहीं है, इसलिए संभवत: एक अधिक उपयुक्त तरीका है जो मैं इस पद्धति को लागू कर सकता था।


3

आम लिस्प, 833

(defun drains (terr dm a b)
  (cond
    ((= (aref dm a b) 1) t)
    ((= (aref dm a b) -1) nil)
    ((or (= a 0) (= b 0)
     (= a (1- (array-dimension terr 0)))
     (= b (1- (array-dimension terr 1)))) t)
    (t (loop for x from -1 to 1
       do (loop for y from 0 to 1
           do (if (and (or (> x 0) (> y 0))
                   (drains terr dm (+ a x) (+ b y))
                   (<= (aref terr (+ a x) (+ b y))
                   (aref terr a b)))
              (progn
                (setf (aref dm a b) 1)
                (return-from drains t)))))
    (setf (aref dm a b) -1)
    nil)))

(defun doit (terr)
  (let ((dm (make-array (array-dimensions terr))))
    (loop for x from 0 to (- (array-dimension terr 0) 1)
       do (loop for y from 0 to (- (array-dimension terr 1) 1)
         do (format t "~a"
            (if (drains terr dm x y)
                (aref terr x y)
                "*"))
         finally (format t "~%")))))

यह गोल्फ के लिए कोई प्रयास नहीं किया गया है, मैं सिर्फ समस्या दिलचस्प पाया। इनपुट मानचित्र का 2D सरणी है। समाधान यह देखने के लिए प्रत्येक वर्ग की जाँच करता है कि क्या यह "नालियाँ" है - एक वर्ग नालियाँ यदि यह बाहरी किनारे पर है या यदि यह नालियों के बराबर या कम ऊँचाई वाले वर्ग के समीप है। अंतहीन रूप से पीछे हटने से बचने के लिए, कोड एक "ड्रेन मैप" (डीएम) रखता है, जहां यह पहले से निर्धारित किए गए वर्गों की जल निकासी स्थिति को संग्रहीत करता है।


आपका वर्णित तर्क बिल्कुल सही नहीं है, क्योंकि यह द्वीप के मामले को सही तरीके से नहीं संभालता है।
कीथ रान्डेल

1

अजगर, 246 चरस

import os
a=list(os.read(0,2e3))
w=a.index('\n')+1
a+=' '*w
def f(p,t):
    if e<a[p]or p in t:return
    t[p]=1
    return'*'>a[p]or any(f(p+d,t)for d in(~w,-w,-w+1,-1,1,w-1,w,w+1))
z=0
for e in a:
    if(' '<e)*~-f(z,{}):a[z]='*'
    z+=1
print''.join(a[:~w])

समाधान प्रत्येक स्थिति से डीएफएस करके काम करता है यह निर्धारित करने के लिए कि क्या भरना है या नहीं।

यदि प्रत्येक पंक्ति पर व्हॉट्सएप को अनुगामी करने की अनुमति है, तो इसे w = 80 का उपयोग करके छोटा किया जा सकता है और इनपुट लाइनों को व्हाट्सएप से 80 वर्णों तक पैडिंग किया जा सकता है।

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