लुआ, 562 535 529 513 507 504 466 458 बाइट्स
इस समय मेरे सबसे बड़े गोल्फ से, मुझे लगता है कि मैं अभी भी 100 बाइट्स काट सकता हूं, जो मैं काम करूंगा, लेकिन इसे एक उत्तर के रूप में पोस्ट कर रहा हूं क्योंकि यह पहले ही कुछ समय ले चुका है :)। मैं सही था, मैंने 100 से अधिक बाइट्स काट लिए हैं! मुझे नहीं लगता कि सुधार के लिए बहुत जगह है।
इस फ़ंक्शन को 2 डी सरणी के साथ प्रति कक्ष एक वर्ण के साथ बुलाया जाना है।
@ धन्यवाद, @ धन्यवाद के साथ काम करते हुए 40 बाइट्स बचाए !
वू हू! 500 के तहत!
function f(m)t=2u=1i=1j=1s=" "::a::if s~=m[i][j]and(i<#m and m[i+1][j]~=s)~=(j<#m[i]and m[i][j+1]~=s)~=(i>1 and m[i-1][j]~=s)~=(j>1 and m[i][j-1]~=s)then goto b end
i,t=i%t+1,#m>t and t==i and t+1or t j=j>1 and j-1or u u=u<#m[1]and j==1 and u+1or u goto a::b::io.write(m[i][j])m[i][j]=s
i,j=i<#m and s~=m[i+1][j]and i+1or i>1 and s~=m[i-1][j]and i-1or i,j<#m[i]and s~=m[i][j+1]and j+1or j>1 and s~=m[i][j-1]and j-1or j
if s==m[i][j]then return end goto b end
Ungolfed
एक बार जब मैं इस गोल्फिंग कर रहा हूँ, स्पष्टीकरण आ जाएगा, इस समय, मैं आपको इस स्रोत कोड का एक पठनीय संस्करण उधार दूंगा: D यहाँ स्पष्टीकरण आया है!
संपादित करें: अद्यतन करने से पहले नवीनतम संशोधन के साथ अद्यतन नहीं, फिर भी गोल्फिंग। एक ही स्पष्टीकरण के लिए चला जाता है
function f(m) -- declare the function f which takes a matrix of characters
t=2 -- initialise the treshold for i
-- when looking for the first end of the snake
u=1 -- same thing for j
i,j=1,1 -- initialise i and j,our position in the matrix
s=" " -- shorthand for a space
::a:: -- label a, start of an infinite loop
if m[i][j]~=s -- check if the current character isn't a space
and(i<#m -- and weither it is surrounded by exactly
and m[i+1][j]~=s) -- 3 spaces or not
~=(j<#m[i]
and m[i][j+1]~=s) -- (more explanations below)
~=(i>1
and m[i-1][j]~=s)
~=(j>1
and m[i][j-1]~=s)
then goto b end -- if it is, go to the label b, we found the head
i,t= -- at the same time
i%t+1, -- increment i
#m>t and t==i and t+1or t -- if we checked all chars in the current range, t++
j=j>1 and j-1or u -- decrement j
u=u>#m[1]and j==1 and u+1or u-- if we checked all chars in the current range, u++
goto a -- loop back to label a
::b:: -- label b, start of infinite loop
io.write(m[i][j]) -- output the current char
m[i][j]=s -- and set it to a space
i,j=i<#m -- change i and j to find the next character in the snake
and m[i+1][j]~=s -- this nested ternary is also explained below
and i+1 -- as it takes a lot of lines in comment ^^'
or i>1
and m[i-1][j]~=s
and i-1
or i,
j<#m[i]
and m[i][j+1]~=s
and j+1
or j>1
and m[i][j-1]~=s
and j-1
or j
if m[i][j]==s -- if the new char is a space
then -- it means we finished
return -- exit properly to avoid infinite
end -- printing of spaces
goto b -- else, loop back to label b
end
इसलिए यहां कुछ विस्तृत व्याख्याएं हैं कि यह कार्यक्रम कैसे काम करता है।
सबसे पहले, चलो लूप लेबल पर विचार करें a
, यह हमें शीर्ष-बाएं कोने के निकटतम छोर को खोजने की अनुमति देता है। यह हमेशा के लिए लूप होगा अगर कोई अंत नहीं है, लेकिन यह एक समस्या नहीं है: डी।
4x4 ग्रिड पर, यह यहाँ साँप की दूरी (बाएं) है, और जिस क्रम को वे (दाईं ओर) देखते हैं
1 2 3 4 | 1 2 4 7
2 3 4 5 | 3 5 8 11
3 4 5 6 | 6 9 12 14
4 5 6 7 | 10 13 15 16
इस चरित्र में से प्रत्येक के लिए, अंत होने के लिए, इसे दो स्थितियों की जांच करनी होगी: - स्थान नहीं होना - बिल्कुल 3 स्थानों से घिरा होना (या बिल्कुल 1 गैर-स्थान)
इन शर्तों को कोड के निम्नलिखित टुकड़े की जाँच की जाती है
r=m[i][j]~=s
and(i<#m and m[i+1][j]~=s)
==not(j<#m[i] and m[i][j+1]~=s)
==not(i-1>0 and m[i-1][j]~=s)
==not(j-1>0 and m[i][j-1]~=s)
and m[i][j]
or r
-- special note: "==not" is used as an equivalent to xor
-- as Lua doesn't know what is a xor...
यह जाँच कर रहा है कि चार स्थान अभिव्यक्ति द्वारा हासिल नहीं किया गया है m[i][j]~=s
।
यह जाँचने पर कि क्या केवल 1 गैर-स्थान से घिरा हुआ है, हमारे आसपास के लिए उपरोक्त शर्तों को xor-ing द्वारा प्राप्त किया जाता है, इसे इस प्रकार नहीं लिखा जा सकता है
m[i+1][j]~=" " ⊕ m[i][j+1]~=" " ⊕ m[i-1][j]~=" " ⊕ m[i][j-1]~=" "
और अंत में, यदि उपरोक्त सभी का सही मूल्यांकन किया जाता है, तो टर्नरी वापस आ जाएगी जो कि अंतिम and
-> में है m[i][j]
। और, हम r
परेशान हैं :)
अब जब हमारे पास सांप का सिर है, तो हम दूसरे छोर तक पहुंच सकते हैं! सांप को Iterating मुख्य रूप से निम्नलिखित नेस्टेड ternaries द्वारा प्राप्त किया जाता है:
i,j=i<#m and m[i+1][j]~=s and i+1or i-1>0 and m[i-1][j]~=s and i-1or i,
j<#m[i]and m[i][j+1]~=s and j+1or j-1>0 and m[i][j-1]~=s and j-1or j
हम फिर से सेट करते हैं i
और j
पुराने मूल्यों को संग्रहीत करने के लिए डमी की आवश्यकता से बचने के लिए वे दोनों एक ही संरचना हैं, और सरल परिस्थितियों का उपयोग करते हैं, इसलिए मैं उन्हें नेस्टेड के रूप में प्रस्तुत करूंगा if
, यह आपको उन्हें पढ़ने की अनुमति देनी चाहिए और आसानी से। :)
i=i<#m and m[i+1][j]~=s and i+1or i-1>0 and m[i-1][j]~=s and i-1or i
इसका अनुवाद किया जा सकता है:
if(i<#m)
then
if(m[i+1][j]~=" ")
then
i=i+1
end
elseif(i-1>0)
then
if(m[i-1][j]~=" ")
then
i=i-1
end
end
झसे आज़माओ!
यह कोड मैं इसे चलाने के लिए उपयोग करता हूं, आप इसे कॉपी-पेस्ट करके ऑनलाइन परीक्षण कर सकते हैं ।
function f(m)t=2u=1i=1j=1s=" "::a::if s~=m[i][j]and(i<#m and m[i+1][j]~=s)~=(j<#m[i]and m[i][j+1]~=s)~=(i>1 and m[i-1][j]~=s)~=(j>1 and m[i][j-1]~=s)then goto b end
i,t=i%t+1,#m>t and t==i and t+1or t j=j>1 and j-1or u u=u<#m[1]and j==1 and u+1or u goto a::b::io.write(m[i][j])m[i][j]=s
i,j=i<#m and s~=m[i+1][j]and i+1or i>1 and s~=m[i-1][j]and i-1or i,j<#m[i]and s~=m[i][j+1]and j+1or j>1 and s~=m[i][j-1]and j-1or j
if s==m[i][j]then return end goto b end
test1={}
s1={
" tSyrep ",
" r p ",
" in Sli ",
" g Sile",
" Snakes n",
"Ser ylt",
"a eh ilS ",
"fe w t ",
" emo h ",
" Sre ",
}
for i=1,#s1
do
test1[i]={}
s1[i]:gsub(".",function(c)test1[i][#test1[i]+1]=c end)
end
f(test1)