लुआ में गोल्फ के लिए टिप्स


21

लूआ में गोल्फिंग के लिए आपके पास क्या सामान्य सुझाव हैं? मैं उन विचारों की तलाश कर रहा हूं, जो सामान्य रूप से कम से कम कुछ हद तक Lua (जैसे "टिप्पणियों को हटाएं" एक उत्तर नहीं है) के लिए विशिष्ट रूप से गोल्फ समस्याओं को लागू करने के लिए लागू किया जा सकता है। कृपया प्रति उत्तर एक टिप पोस्ट करें।


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

जवाबों:


9

पहले से ही पोस्ट किए गए लोगों के अलावा, यहां कुछ तरकीबें बताई गई हैं, जो किसी खास क्रम में समय के साथ इकट्ठी हो जाती हैं ...

  • फ़ंक्शन कॉल के लिए जो केवल एक पैरामीटर को प्रतीक द्वारा ( "सीढ़ियों के लिए, {तालिकाओं के लिए) सीमांकित किया गया है , पैरामीटर को कोष्ठक के चारों ओर लपेटने की आवश्यकता नहीं है।
    उदाहरण के लिए, करने के बजाय print("hello"), आप बस कर सकते हैं:print"hello"

  • जितना संभव हो उतना व्हाट्सएप निकालें - यह विशेष रूप से एक प्रतीक के बाद करना आसान है जो तार (या एक खोलने से पहले) को बंद करता है, फ़ंक्शन कॉल, टेबल ...
    इसके बजाय print(42) a=1आप कर सकते हैं print(42)a=1। अन्य उदाहरण print(a and-1 or-2):।

  • जब आप कर सकते हैं टर्नरी ऑपरेटर का उपयोग करें! इसके बजाय if a>0 then print("hello") else print("goodbye") end, प्राथमिकता दें print(a>0 and "hello" or "goodbye")। अधिक जानकारी यहाँ
    (यह वास्तव में बेहतर भी प्राप्त कर सकते हैं: print(a>0 and"hello"or"goodbye"))

  • जब आप कर सकते हैं तो कोलोन-कॉल सिंटैक्टिक शुगर का उपयोग करें: इसके बजाय string.rep(str,12), करें str:rep(12)। यह भी इस तरह से गैर-चर पर काम करता है (और केवल इस तरह से):("a"):rep(5)

  • करने के बजाय tonumber(str)बस करोstr+0

  • बिना किसी पैरामीटर के फ़ंक्शंस के लिए, उन्हें सामान्य तरीके से परिभाषित करने के बजाय ( function tick() blabla() end), आप कर सकते हैं: ticks=loadstring"blabla()"जो सामग्री के आधार पर 1 या अधिक बाइट्स बचाता है। इसके अलावा, यदि आप कई कार्यों को परिभाषित करते हैं, तो loadstring1-चर चर से पहले स्थानीयकरण करें और आप बहुत सारे बाइट्स बचाएंगे;)। इस ट्रिक के लिए जिम बौवेन्स को श्रेय।

  • Lua सशर्त परीक्षणों में खाली स्ट्रिंग (और 0अन्य भाषाओं के विपरीत) को सही मानती है , इसलिए, उदाहरण के लिए, ऐसा करने के बजाय while 1 do ... end, 1 बाइट लिखकर सहेजेंwhile''do ... end


(लोडस्ट्रिंग ट्रिक को जोड़ा गया)
एड्रिएब

2
0 एक
सत्य

एक और str+0समतुल्य है ~~str, यह पूर्ववर्ती के लिए उपयोगी हो सकता है
फेलिप नारदी बतिस्ता

@FelipeNardiBatista हालांकि यह केवल लुआ 5.3+ पर समर्थित है
Adriweb

5

मैंने पहले ही एक के बारे में सोचा है। मुझे नहीं पता कि यह कुछ अन्य भाषाओं में काम करता है, लेकिन लुआ केवल एक ही है जो मुझे पता है कि क्या आप चर में कार्यों को स्टोर करने की अनुमति देते हैं। इसलिए यदि उदाहरण string.subआपके प्रोग्राम में कई बार उपयोग किया जाता है, उदाहरण के लिए उपयोग करें s=string.sub


4
यह कई अन्य भाषाओं जैसे पायथन और रूबी में भी काम करता है।
nyuszika7h

4
जावास्क्रिप्ट और हास्केल में फ़ंक्शन मान भी हो सकते हैं।
गर्वित हेकलर

यह स्ट्रिंग मान वाले किसी भी चर के लिए s=("").subया उसके बराबर है । s=a.suba
ईगोर स्क्रीप्टुनॉफ

इसे प्रथम श्रेणी के कार्य कहा जाता है
रेडवॉल्फ कार्यक्रम

5

यह गोल्फ के लिए एक बहुत अच्छी भाषा है ... लेकिन कुछ सामान्य सुझाव जो मन में आते हैं:

  • सशर्त से बचने की कोशिश करें, क्योंकि if... then... else...end एक प्रमुख बर्बादी है।
  • इसके बजाय, उन भाषा निर्माणों पर ध्यान देने की कोशिश करें जो छोटे हैं, जैसे for i=1,5 do
  • #ऑपरेटर गोल्फ के लिए बहुत महान (और सामान्य रूप में) है।

5

अपने अनंत लूप को छोटा करें

जब आपको एक अनंत लूप का उपयोग करना होता है, तो आप ए का उपयोग करने के बारे में सोच सकते हैं while, लेकिन इसके बजाय एक लेबल का उपयोग करना 2 बाइट से छोटा होता है:

while''do end
::a::goto a

जितना हो सके कम जगह का इस्तेमाल करें

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

x=0>1 and 0or 1print(x)

स्थान को हटाने की संभावना संख्या के बाद के अक्षर पर निर्भर करती है, यहां वह पत्र है जो आपको ऐसा करने की अनुमति नहीं देगा:

a,b,c,d,e,f            -- They would be interpreted as hexadecimal
x                      -- only fail when after a 0, other number are fine
                       -- (0x indicates the following is an hexadecimal number)

इसका उपयोग करके, और ध्यान दें कि आप अपने चर को कैसे कॉल करते हैं, आप अपने अधिकांश स्रोत कोड को स्थान-मुक्त बना सकते हैं।

पहले से ही यहां एक उदाहरण उठा है, और इस सलाह का उपयोग करते हुए, यहां एक और बाइट है जिसे आप मुंडा सकते हैं :)।

print(a and-1 or-2)
print(a and-1or-2)

सही इनपुट विधि का उपयोग करें

यदि हम प्रत्येक प्रमुख प्रकार के इनपुट के लिए बॉयलरप्लेट और लागत को देखते हैं , तो यहां हमारे पास क्या है:

function f(x)x end
io.read()
arg[1]

इस पद्धति में से प्रत्येक हमें 1 इनपुट लेने की अनुमति देता है, जिसमें फ़ंक्शन सबसे भारी लागत के साथ होता है (लेकिन हमें इनपुट के रूप में एक टेबल लेने की अनुमति देता है)

अब हम देख सकते हैं कि यदि आप गोल्फ चाहते हैं तो कमांड-लाइन तर्क का उपयोग करना रास्ता है, लेकिन जागरूक रहें: यह और भी छोटा हो सकता है

arg[1]
...

...Lua में थोड़ा विशेष हैं, यह एक चर के पैक सामग्री से युक्त है arg, या एक variadic समारोह के मामले में पैक मानकों।

जब आपको एक से अधिक इनपुट प्राप्त करने होंगे, और उनमें से प्रत्येक का उपयोग करना होगा, तो उन्हें एक चर में सहेजना अच्छा हो सकता है। यहाँ चर में 2 इनपुट को बचाने के कुछ तरीके दिए गए हैं

a=arg[1]b=arg[2]    -- highly un-efficient, costs 8 bytes by variable
a,b=unpack(arg)     -- costs 15, but at least doesn't depends on the number of argument
a,b=...             -- only costs 7

और यहां वे सबसे छोटी कॉल हैं जो आप चर के बिना कर सकते हैं:

...     -- using a allow a gain of 1-2 bytes at each use
arg[2]  -- using b allow a gain of 4-5 bytes at each use

उस बिंदु से जहां आपके पास 3 तर्क हैं, या जब आप 2 तर्कों का उपयोग करते हैं, तो दो बार उपयोग किए जाने के साथ, आप पहले से ही बाइट प्राप्त कर रहे हैं a,b=...! :)

लगभग कभी उपयोग नहीं अगर!

ऐसे मामलों के पास नहीं है जहाँ एक if / फारस / if कथन का उपयोग करने पर एक टर्नरी से कम खर्च होगा। इस तरह के एक बयान के लिए बॉयलरप्लेट वास्तव में भारी है:

-- exemple with dumb values
if 1>0then v=1 else v=0 end
v=1>0 and 1or 0

एक सरल उदाहरण के साथ, आप पहले से ही 12 बाइट्स बचाते हैं, जब आपको कुछ और काम करना होता है, तो यह अधिक से अधिक महत्वपूर्ण हो जाता है, इसलिए इसके बारे में पता होना चाहिए!

इसके अलावा, लुआ में ternaries विशेष हैं , वहाँ कुछ शर्त है कि वे कैसे काम करते हैं, रुचि रखने वालों के लिए, मैं इसे नीचे :

लुआ में टेरानरीज़ का रूप है <condition> and <case true: have to be a true value> or <case false: can be anything>

सबसे पहले, आइए देखें की सत्य तालिका or। A orको एक फ़ंक्शन के रूप में माना जा सकता है: यह हमेशा एक मान लौटाता है, यहाँ वह मान लौटाता है:

x | y ||x or y
------||-------
0 | 0 ||   y
0 | 1 ||   y
1 | 0 ||   x
1 | 1 ||   x

यही कारण है कि हमें अपनी त्रिगुट का निर्माण करने की अनुमति देता है।

andक्या हमें स्थिति का मूल्यांकन करने की अनुमति है, यह हमेशा वापस आ जाएगी yअगर x and yमूल्यांकन करता है सच करने के लिए।

इसके साथ समस्या यह है कि अगर हम चाहते हैं कि यह विफल हो जाए nilया falseजब हालत हो तो वापस लौटाया जाए false। उदाहरण के लिए, स्थिति हमेशा सही होने के बावजूद, निम्नलिखित 5 हमेशा वापस आ जाएंगे।

v = true and false or 5

यह समझने के लिए कि यह कैसे काम करता है (यह तब आपके लिए उपयोगी होगा जब आप उन्हें घोंसला बनाना चाहते हों) :)

-- let's use our dumb ternary
= true and false or 5
-- and statement will be evaluated first, leading to
= false or 5
-- and we saw how the or works
= 5

प्रति उत्तर एक टिप, कृपया।
ATaco

ध्यान दें कि "कम से कम स्थान का उपयोग करें" चाल केवल लुआ 5.2 और बाद में काम करती है।
एड्रिएब

4

मैंने कई युक्तियों को भी संकलित किया है। मुझे यकीन है कि मेरा कुछ पहले से ही बताए गए लोगों के साथ ओवरलैप होगा, लेकिन मैं उन्हें किसी भी तरह से और अधिक पूर्ण उत्तर बनाने के नस में शामिल करूंगा।


चर के लिए दोहराया कार्यों असाइन करें

लुआ आपको चर को कार्य सौंपने की अनुमति देता है। यहां तक ​​कि एक चरित्र चर। इसका मतलब है यदि आप फ़ंक्शन दोहराते हैंstring.sub(x, y) दो बार से अधिक , तो आपको इसे एक चर पर असाइन करने से लाभ मिलेगा।

एक चर (69 वर्ण) को निर्दिष्ट किए बिना:

print(string.sub(x, y))
print(string.sub(x, y))
print(string.sub(x, y))

एक चर (51 वर्ण) को असाइन करना:

s=string.sub
print(s(x,y))
print(s(x,y))
print(s(x,y))

ऐसे मामले हैं जहां आप इसे एक कदम आगे ले जा सकते हैं। Lua एक OOP को स्ट्रिंग हेरफेर करने की अनुमति देता है, जैसे: str:sub(x, y)या str.sub(x, y)यह हमारे कोड के लिए नए विकल्प खोलता है। आप फ़ंक्शन को एक चर असाइन कर सकते हैं, जैसा कि दिखाया गया है (46 अक्षर)।

s=z.sub
print(s(x, y))
print(s(x, y))
print(s(x, y))

तार को पार्स करने के लिए सबसे कुशल तरीके का उपयोग करें

आप एक forलूप का उपयोग करके और string.subलुआ में चरित्र द्वारा चरित्र को पुनरावृत्त करने के लिए पा सकते हैं । कभी-कभी यह आपकी आवश्यकताओं के आधार पर सबसे अच्छा काम कर सकता है, लेकिन अन्य बार, string.gmatch कम वर्णों में काम करेगा। यहाँ दोनों का एक उदाहरण दिया गया है:

s=io.read()
for a = 1, s:len() do
    print(s:sub(a, a))
end 

for i in io.read():gmatch('.') do
    print(i)
end

और जब गोल्फ, अंतर अधिक उल्लेखनीय है:

s=io.read()for a=1,s:len()do print(s:sub(a, a))end

for i in io.read():gmatch'.'do print(i)end

व्हाट्सएप का अनुकूलन करने के लिए पुनर्गठन कार्य

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

  • वैरिएबल असाइन करना:

     x,y=io.read(),0 print(x)
     vs.
     y,x=0,io.read()print(x)
    
  • यदि कथन:

     if x:sub(1,1)==1 then
     vs
     if 1==x:sub(1,1)then
    

संभव सबसे कम वर्ण लौटाएं

यदि आपको एक सही या गलत मान वापस करना चाहिए, तो ऐसा लगता है कि आपको वापसी मूल्य के लिए कम से कम 5 वर्णों का उपयोग करना चाहिए। वास्तव में निम्नलिखित काम करता है:

return true
return false
vs
return 1>0
return 0>1

महान युक्तियाँ, मैंने आपके पोस्ट को संपादित करने का सुझाव देने के लिए स्वतंत्रता ली है। केवल nilऔर केवल falseलुआ में झूठे का मूल्यांकन करता है, बाकी सब कुछ सच है, इसलिए आपके द्वारा प्रतिस्थापित करने के बारे में सुझाव x==0, x==""और झूठे हैं। मैं वर्तमान में इसे बदल रहा हूं :)। x==''xnil
काटनकेयो

आह, आप सही हैं। इसे ठीक करने के लिए धन्यवाद!
Skyl3r

2

ये केवल लुआ हैं (मुझे लगता है) अनुकूलन:

स्ट्रिंग्स स्वचालित रूप से संख्याओं में परिवर्तित हो जाते हैं जब उन पर अंकगणितीय संचालन करते हैं। बस सशर्त बयानों के लिए देखें, वे स्वचालित रूप से परिवर्तित नहीं होते हैं। अंतरिक्ष की बचत करते समय संख्या के रूप में उपयोगकर्ता इनपुट लेने के लिए यह बहुत अच्छा है।

दो चर की सामग्री को स्विच करने के लिए एक अस्थायी चर की आवश्यकता नहीं होती है। a,b=b,aa और b के मूल्यों को स्वैप करेगा।

इसके अलावा, जो ऊपर कहा गया था, उस पर विस्तार करने के लिए, कोई भी अल्फ़ान्यूमेरिक वर्ण एक गैर अल्फ़ान्यूमेरिक वर्ण को छू सकता है। तो a,b=io.read():match"(.+)/(.+)"u,v=a,bव्हॉट्सएप की कमी के साथ भी एक परफेक्ट, वर्किंग स्क्रिप्ट है।


2

स्थानीय वैरिएबल असाइनमेंट को मिलाएं

के बजाय:

local a=42
local b=17
local c=99

समानांतर असाइनमेंट का उपयोग करें:

local a,b,c=42,17,19

प्रत्येक चर के लिए 6 बाइट्स बचाए गए!

अप्रयुक्त फ़ंक्शन पैरामीटर के माध्यम से स्थानीय चर की घोषणा करें

के बजाय:

function foo(a,b) local c,d ... end
function bar(a,b) local c,d=42,17 ... end

उपयोग

function foo(a,b,c,d) ... end
function bar(a,b,c,d) c,d=42,17 ... end

6 बाइट्स सहेजे गए (प्रत्येक चर के लिए माइनस 1-2 बाइट्स जो डुप्लिकेट हो सकते हैं)।


1
डाउनवोटेड क्योंकि वहाँ बिल्कुल कोई मामला नहीं है जहाँ का उपयोग localकरना उचित है जब गोल्फ, क्योंकि आपको बस एक अलग नाम का उपयोग करना होगा। हम 7 charachters संयोजन करने के लिए 7 charachters और स्ट्रिंग सूचकांक तालिकाओं के लिए ऊपर सभी के नाम इस्तेमाल कर सकते हैं इससे पहले कि हम कुछ है कि स्थानीय लोगों का उपयोग करने से फायदा हो सकता है कम पड़ रहा है
Katenkyo

1

वैराडिक कार्य

मुख्य चर समारोह जो आपको परेशान करेगा print()। उदाहरण के लिए, जब आप इसका उपयोग कर रहे हैं तो String.gsub()यह आपके द्वारा संशोधित स्ट्रिंग और समय की संख्या को प्रिंट करेगाgsub

उस दूसरे आउटपुट को दबाने के लिए, आप gsubको केवल एक मान वापस करने के लिए मजबूर करने के लिए परेंस में एनकैप्सुलेट करें

print(String.gsub("aa",".","!"))    -- outputs "!!    2\n"
print((String.gsub("aa",".","!")))  -- outputs "!!\n"

1

जानिए कैसे करें आउटपुट

लुआ में आउटपुट करने की दो मुख्य विधि है

io.write()    -- outputs without trailing newline
print()       -- outputs with trailing new line and shorter by 3 bytes

जब आपको कई बार कॉन्टेक्ट करना होता है, तो आप io.write()मानक कॉन्सटेबल ऑपरेटर के बजाय एक अक्षर वेरिएबल को असाइन करके छोटा कर सकते हैं..

i(a)    -- i was defined as io.write
s=s..a

आप कुछ अपफ्रंट का भुगतान करते समय प्रत्येक कॉल पर 2 बाइट प्राप्त करते हैं

i=io.write  -- longer by 6 bytes
s=""

आप तीसरे स्थान पर भी हैं, और चौथे पर बाइट प्राप्त करना शुरू करते हैं।


3
यह है printऔर नहीं printf!
वैल का कहना है कि मोनिका

@ ओवल वॉ, मुझे यह भी नहीं पता कि मैं वह गलती कैसे कर सकता हूं। इसे इंगित करने के लिए धन्यवाद, मैं संपादित करता हूं
काटेनको

1

कोई विशेष क्रम में युक्तियों का एक गुच्छा:

  • stringबहुत लंबा नाम है। कुशलता से, के ('').charरूप में ही है string.char। यहां तक ​​कि अगर आप इसे चर पर अर्धविराम के साथ उपयोग करते हैं, तो भी बेहतर परिणाम प्राप्त किए जा सकते हैं: a=...; print(a:sub(1, 5))लेकिन कुछstring कार्य इनपुट के रूप में तार नहीं लेते हैं।
  • अधिकांश मामलों के लिए लुआ में स्ट्रिंग्स और संख्याओं के बीच स्वचालित रूपांतरण है, इसलिए tonumber और +0अक्सर केवल बाइट्स बर्बाद करते हैं।
  • के load'your function code here'बजाय हमेशा उपयोग करेंfunction()your function code here end । उपयोग समारोह का उपयोग तर्क...अंदर ।
  • Lua में कुछ स्ट्रिंग फ़ंक्शंस का उपयोग अनपेक्षित तरीकों से किया जा सकता है! उदाहरण के लिए,a:gsub('.',load'my function') एक स्ट्रिंग में वर्णों पर पुनरावृति करने का सबसे छोटा तरीका प्रतीत होता है
  • जबकि स्ट्रिंग इंजन शक्तिशाली है, पैटर्न के रूप में उपयोगकर्ता इनपुट का उपयोग करते समय इसकी शक्ति से सावधान रहें! उसके कारण, आपको a:find('.',1,1)(इस समस्या का परीक्षण करने के लिए, %अपने इनपुट में विभिन्न स्थानों को शामिल करने और परिणामों की जांच करने के लिए प्रयास करना होगा)। पैटर्न के रूप में इनपुट को पार्स करने की कोशिश के कारण अनगिनत विचार टूट गए।
  • nil तीन बाइट्स है, _ एक है (यह सिर्फ यादृच्छिक नाम है जो सबसे अधिक संभावना नहीं है)। साथ ही, कोई भी अंक सत्य मान के रूप में काम करेगा।
  • अपने तर्क के पीछे जानें x and i or o। यह सिर्फ एक टर्नरी ऑपरेटर नहीं है - यह एक पूर्ण तार्किक अभिव्यक्ति है। वास्तव में, इसका मतलब निम्न है: "यदि सत्य है, तो xप्रयास करें i। यदि या तो एक्स या मैं गलत है, तो ओ वापस करें"। तो अगर iसत्य नहीं है, तो परिणाम है o। इसके अलावा, दोनों andया orभागों को छोड़ा जा सकता है ( x and i,x or o )।
  • के बजाय एक के बाद उपयोग पूर्णांक विभाजन math.floor: 5.3//1==5.0। कृपया ध्यान दें कि परिणामी संख्या हमेशा इनपुट एक (पूर्णांक / फ्लोट) के प्रकार का अनुसरण करती है।

1
"इसके अलावा, कोई भी अंक सत्य मान के रूप में काम करेगा।" बस यह विस्तृत करना चाहता था कि इसमें 0 शामिल हैं, जो कि C / C ++ बैकग्राउंड के कुछ कोडर्स के लिए बहुत सहज नहीं हो सकता है।
इउफ्लक
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.