"आलसी क्रमबद्ध करें" को लागू करें


44

मुझे संख्याओं की सूची को क्रमबद्ध करना है, लेकिन मैं सुपर आलसी हूं। यह वास्तव में कठिन है कि सभी संख्याओं को कैसे स्वैप किया जाए, जब तक कि वे सभी बढ़ते हुए क्रम में न हों, इसलिए मैं अपने स्वयं के एल्गोरिथ्म के साथ आया हूं जो गारंटी देगा कि नई सूची क्रमबद्ध है। यहां देखिए यह कैसे काम करता है:

आकार N की सूची के लिए , हमें N-1 पुनरावृत्तियों की आवश्यकता होगी । प्रत्येक पुनरावृत्ति पर,

  • जांचें कि N'th नंबर N + 1'th नंबर से छोटा है या नहीं । यदि यह है, तो ये दो नंबर पहले से ही क्रमबद्ध हैं, और हम इस पुनरावृत्ति को छोड़ सकते हैं।

  • यदि वे नहीं हैं, तो आपको पहले एन संख्याओं को लगातार घटाना होगा जब तक कि ये दो संख्याएं क्रम में न हों।

चलिए एक ठोस उदाहरण लेते हैं। मान लीजिए कि इनपुट था

10 5 7 6 1

पहली पुनरावृत्ति पर, हम 10 और 5 की तुलना करेंगे। 10 5 से बड़ा है, इसलिए हम इसे छोटा होने तक घटाते हैं:

4 5 7 6 1

अब हम 5 और 7. 5 की तुलना 7 से छोटा करते हैं, इसलिए हमें इस पुनरावृत्ति पर कुछ भी करने की आवश्यकता नहीं है। तो हम अगले पर जाते हैं और 7 और 6 की तुलना करते हैं। 7 6 से बड़ा है, इसलिए हम पहले तीन नंबरों को घटाते हैं जब तक कि यह 6 से छोटा न हो, और हमें यह मिलता है:

2 3 5 6 1

अब हम 6 और 1 की तुलना करते हैं। फिर से, 6 1 से बड़ा है, इसलिए हम पहले चार नंबरों को घटाते हैं जब तक कि यह 1 से छोटा न हो, और हम यह करते हैं:

-4 -3 -1 0 1

और हम कर रहे हैं! अब हमारी सूची एकदम सही क्रम में है। और, चीजों को और बेहतर बनाने के लिए, हमें केवल N-1 बार सूची के माध्यम से पुनरावृत्त करना पड़ा , इसलिए यह एल्गोरिथ्म सॉर्ट करता है O (N-1) समय में सूची, जो मुझे पूरा यकीन है कि सबसे तेज एल्गोरिथ्म है ।²

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

यहाँ कुछ उदाहरण हैं:

Input: 10 5 7 6 1
Output: -4 -3 -1 0 1

Input: 3 2 1
Output: -1 0 1

Input: 1 2 3
Output: 1 2 3

Input: 19
Output: 19

Input: 1 1 1 1 1 1 1 1 1 
Output: -7 -6 -5 -4 -3 -2 -1 0 1 

Input: 5 7 11 6 16 2 9 16 6 16
Output: -27 -25 -21 -20 -10 -9 -2 5 6 16

Input: -8 17 9 7
Output: -20 5 6 7

हमेशा की तरह, यह , इसलिए सबसे छोटा प्रोग्राम लिखें जो आप कर सकते हैं!


What इसका मतलब यह नहीं है कि यह कैसा लगता है इसका मतलब है, लेकिन यह तकनीकी रूप से सच है

Kid मैं पूरी तरह से मजाक कर रहा हूं, कृपया मुझसे नफरत मत करो


6
मुझे लगता है कि अगर आप इसे इस तरह से करते हैं तो आप आलसी नहीं हैं
Jörg Hülsermann

4
@ JörgHülsermann अच्छी तरह से कुछ पूर्णांक बहुत भारी हैं ... बिल्कुल ऐसा वजन उठाने के मूड में नहीं, बेहतर है कि आप केवल शीर्ष सामान बाहर निकाल दें
एरिक आउटगोल्फर

21
<sarcasm>यह छँटाई एल्गोरिथ्म वास्तव में अभी भी O(N^2)समय जटिलता में देखता है क्योंकि आपको सूची में सभी पहले से एक्सेस किए गए आइटमों से गुजरना पड़ता है ताकि उन्हें कम किया जा सके। मैं इसके बजाय पीछे की ओर सूची से गुजरने की सलाह देता हूं और आवश्यकतानुसार केवल एक नंबर प्रति कदम घटाता हूं । यह आपको सच्ची O(N)जटिलता देगा! </sarcasm>
मूल्य इंक

1
@ValueInk O(n^2)मेमोरी एक्सेस के मामले में, लेकिन O(n)तुलना के लिए नहीं है ?
कोल जॉनसन

7
@ColeJohnson तकनीकी रूप से हाँ, लेकिन समय जटिलता को एल्गोरिथ्म के सभी चरणों को ध्यान में रखने की आवश्यकता है। आपको अभी भी प्रत्येक पुनरावृत्ति पर पिछले सभी सूचकांकों के माध्यम से चलना है, इसलिए यह अभी भी बाहर आता है O(N^2)
मूल्य इंक

जवाबों:


12

जेली ,  14 12 11  9 बाइट्स

-2 बाइट्स ETHproductions के लिए धन्यवाद (न्यूनतम रंजक का उपयोग करें «)

I’«0Ṛ+\Ṛ+

पूर्णांकों की सूची लेने और लौटाने वाली एक विचित्र लिंक।

इसे ऑनलाइन आज़माएं! या परीक्षण सूट देखें।

मुझे नहीं लगता कि यह आलसी ™ के लिए पर्याप्त है!

कैसे?

I’«0Ṛ+\Ṛ+ - Link: list of integers, a              e.g. [ 8, 3, 3, 4, 6, 2]
I         - increments between consecutive items of a   [-5, 0, 1, 2,-4 ]
 ’        - decrement (vectorises)                      [-6,-1, 0, 1,-5 ]
   0      - literal 0
  «       - minimum of decremented increments and zero  [-6,-1, 0, 0,-5 ]
    Ṛ     - reverse                                     [-5, 0, 0,-1,-6 ]
      \   - cumulative reduce with:
     +    -   addition                                  [-5,-5,-5,-6,-12]
       Ṛ  - reverse                                     [-12,-6,-5,-5,-5]
        + - addition (with a)                           [-4,-3,-2,-1, 1, 2]


8

जावास्क्रिप्ट (ईएस 6), 61 बाइट्स

a=>a.map((b,i)=>a=(b-=a[i+1])>0?a.map(c=>i--<0?c:c-b-1):a)&&a

परीक्षण के मामलों


7

जेली , 12 बाइट्स

I»1U
0ị;Ç_\U

इसे ऑनलाइन आज़माएं!

यह काम किस प्रकार करता है

I»1U  Helper link. Argument: l (list of integers)
I     Compute the increments (difference between items) of l.
 »1   For each item n, take the maximum of n and 1.
   U  Reverse.

0ị;Ç_\U  Main link. Argument: l (list of integers)
   Ç     Call the helper link with argument l.
  ;      Concatenate this with
0ị       the 0th last item of the (1-indexed) l. (Can't use Ṫ because it modifies l)
    _\   Cumulatively reduce the result by subtraction.
      U  Reverse.

नाटक में मूल विचार यह है: यदि आप इनपुट और आउटपुट सरणियों को उल्टा करते हैं, तो आउटपुट केवल 0 के प्रत्येक डेल्टा के साथ इनपुट है या -1 के साथ बदल दिया गया है। उदाहरण के लिए:

[10,  5,  7,  6,  1]   input
[ 1,  6,  7,  5, 10]   reverse
[   5,  1, -2,  5  ]   deltas
[  -1, -1, -2, -1  ]   min(deltas, -1)
[ 1, -1, -2, -1, -1]   reverse and concat the last item of the original
[ 1,  0, -2, -3, -4]   re-apply deltas
[-4, -3, -2,  0,  1]   reverse

5

k, 20 बाइट्स

{x-|+\0,1_0|1+-':|x}

इसे ऑनलाइन आज़माएं।

स्पष्टीकरण:

{                  } /function, x is input
                 |x  /reverse x
              -':    /difference between every element
            1+       /add one to each difference
          0|         /make minimum difference be 0
      0,1_           /swap first difference with a 0
    +\               /cumulative sum
   |                 /reverse again
 x-                  /subtract from x

4

हास्केल, 56 बाइट्स

a#(x:y:z)=map(+min(y-x-1)0)(a++[x])#(y:z)
a#x=a++x
([]#)

इसे ऑनलाइन आज़माएं!

सूची के पहले भाग को पैरामीटर में रखें a। हर कदम पर अगले तत्व जोड़ xके अंत तक aऔर कम से कम से एक के सभी तत्वों को बढ़ाने (y-x-1)और 0



3

सी #, 76 बाइट्स

a=>{for(int d=0,i=a.Length-1;i>0;a[--i]-=d)d=a[i-1]-d<a[i]?d:a[i-1]-a[i]+1;}

यह जगह में सूची को संशोधित करता है। यह सूची में पीछे की तरफ जाता है और प्रत्येक नंबर पर लागू करने के लिए डेल्टा का रनिंग कुल रखता है।


2

जावास्क्रिप्ट (ईएस 6), 59 बाइट्स

f=([n,...a],p=a[0]-n)=>a+a?[(a=f(a))[0]-(p>1?p:1),...a]:[n]

वाह। मैं JS समाधान लिखने वाला था, लेकिन फिर मैंने यह देखा। मुझे लगता है कि मापदंडों में उस तरह के प्रसार ऑपरेटर का उपयोग करना
जरूरी नहीं था

आप f=दो बाइट्स को बचाने के लिए JS जवाबों के लिए रवाना हो सकते हैं
andrewarchi

@andrewarchi धन्यवाद, लेकिन इस विशेष फ़ंक्शन को खुद को कॉल करने की आवश्यकता है ( f(a)) इसलिए इसे अभी भी नाम की आवश्यकता है।
ETHproductions

मैं भूल गया कि यह पुनरावर्ती था
andrewarchi

2

ब्रेन-फ्लैक , 153 बाइट्स

{(({})<>[({})])(({}({}))[({}[{}])])<>(([{}]({})))([({}<(())>)](<>)){({}())<>}{}{((<{}>))<>{}}{}<>{}{{}({}<>{}())((<>))}{}{}}{}<>{}([]){{}({}<>)<>([])}<>

इसे ऑनलाइन आज़माएं!

इसमें शामिल हैं +1के लिए -rझंडा।

#While True
{

    #Push the last value left in the array minus the counter onto the alternate stack
    (({})<>[({})])

    #Put the counter back on top of the alternate stack
    (({}({}))[({}[{}])])

    #Toggle
    <>

    #Find the difference between the last two inputs left on the array
    (([{}]({})))

    #Greater than or equal to 0?
    ([({}<(())>)](<>)){({}())<>}{}{((<{}>))<>{}}{}<>{}

    #If So:
    {

      #Pop the truthy/falsy value
      {}

      #Increment the counter by the difference between elements +1
      ({}<>{}())

      #Push two falsys
      ((<>))

    #Endwhile
    }

    #Pop the two falsys
    {}{}

#Endwhile
}

#Pop the falsy

{}

#Toggle back
<>

#Pop the counter

#Reverse the stack
{}
([]){{}({}<>)<>([])}<>

2

आर, 56 बाइट्स

function(s){s-c(rev(cumsum(rev(pmax(0,-diff(s)+1)))),0)}


1
का अच्छा उपयोग diff, मैं यह पता लगाने की कोशिश कर रहा था कि उस काम को कैसे प्राप्त किया जाए ... वैसे, आप फ़ंक्शन बॉडी के चारों ओर -2 बाइट्स से छुटकारा पा सकते हैं, लेकिन बेहतर अभी तक, आप s=scan()एक फ़ंक्शन के बजाय उपयोग कर सकते हैं कुछ और बाइट्स को बचाने के लिए परिभाषा। यह बहुत अच्छा होगा यदि आप इसे ऑनलाइन आज़माने के लिए एक लिंक शामिल करेंगे ताकि अन्य लोग यह सत्यापित कर सकें कि यह कोड सभी परीक्षण मामलों के लिए काम करता है।
ग्यूसेप

कोई चिंता नहीं! हम सभी कहीं न कहीं :)
Giuseppe

1

जावास्क्रिप्ट (ईएस 6), 68 बाइट्स

a=>a.map((v,i)=>(d=v-o[i+1]+1)>1?o=o.map((v,j)=>j>i?v:v-d):0,o=a)&&o

इनपुट और आउटपुट पूर्णांकों की एक सरणी है।

टेस्ट स्निपेट

f=
a=>a.map((v,i)=>(d=v-o[i+1]+1)>1?o=o.map((v,j)=>j>i?v:v-d):0,o=a)&&o
<input id=I oninput="O.value=f(this.value.split` `.map(x=>+x)).join` `">
<input id=O disabled>


1

जावास्क्रिप्ट (ईएस 6), 50 बाइट्स

f=a=>(b=[...a]).some((_,i)=>a[i]-->=a[i+1])?f(a):b

स्पष्टीकरण:

यह एक पुनरावर्ती समाधान है, जो पहले सरणी को क्लोन करता है, फिर सभी मानों को तब तक घटाता है जब तक कि कोई तत्व सरणी में अगले तत्व के बराबर या उससे अधिक न हो।

फ़ंक्शन तब तक खुद को कॉल करता है जब तक कोई भी तत्व क्रम से बाहर न हो। जब तत्वों को अंततः सॉर्ट किया जाता है, तो क्लोन वापस आ जाता है। (हम सरणी को स्वयं वापस नहीं कर सकते, क्योंकि some()विधि ने उसके सभी तत्वों को घटा दिया होगा, जिससे वे सभी बंद हो जाएंगे।)

परीक्षण के मामलों:

f=a=>(b=[...a]).some((_,i)=>a[i]-->=a[i+1])?f(a):b

console.log(f([10,5,7,6,1])+'');
console.log(f([1,1,1,1,1,1,1,1,1])+'');
console.log(f([5,7,11,6,16,2,9,16,6,16])+'');
console.log(f([19])+'');
console.log(f([-8,17,9,7])+'');
console.log(f([1,2,3,4,5,6,7])+'');


1

एसडब्ल्यूआई-प्रोलॉग, 194 बाइट्स

:-use_module(library(clpfd)).
f([],[],_,_).
f([A|B],[M|N],P,D):-A#=M-D-E,A#<P,abs(M,S),T#=S+1,E in 0..T,label([E]),f(B,N,A,D+E).
l([],[]).
l(A,B):-reverse(Z,B),f([X|Y],Z,X+1,0),reverse(A,[X|Y]).

इसे ऑनलाइन यहाँ आज़माया जा सकता है: http://swish.swi-prolog.org/p/LazySort.pl

आप पूछते हैं l(L, [10,5,7,6,1]).जो कहता है "एल के लिए हल, जहां एल इस सूची का आलसी सॉर्ट किया गया संस्करण है"।

दो कार्य हैं:

  • lazysorted (A, B) - कहता है कि A, B का आलसी संस्करण है, यदि वे दोनों खाली सूची हैं, या यदि A को B को उल्टा करके प्राप्त किया जा सकता है, तो सूची को चलाने के लिए एक सहायक फ़ंक्शन को कॉल करके और एक संचायक के साथ घटाव करें। प्रत्येक मूल्य को पिछले एक से कम धक्का, और चारों ओर सही तरीके से उस परिणाम का उल्टा।
  • fहेल्पर दो सूचियों से मेल खाता है, सूची में पिछली संख्या का मूल्य और एक रोलिंग अंतर संचायक, और वर्तमान सूची स्थिति के नए मूल्य के लिए हल करता है मूल मान शून्य से अंतर संचायक होता है, वैकल्पिक रूप से इस पर बल देने के लिए आवश्यक एक नया मान होता है। सूची में पिछली संख्या के नीचे का मूल्य, और fअब बढ़ी हुई अंतर संचायक के साथ पुन: सूची की पूंछ के लिए हल करना चाहिए।

स्विश पर परीक्षण मामलों का स्क्रीनशॉट:

छवि स्विश पर चल रहे परीक्षण मामलों को दिखाती है


0

जावास्क्रिप्ट (ईएस 6), 61 बाइट्स

a=>a.reduceRight((r,e)=>[e-(d=(c=e-r[0]+1)>d?c:d),...r],d=[])

सबसे छोटा समाधान नहीं है, लेकिन मैं उपयोग करने का अवसर नहीं दे सका reduceRight


0

सी # (.NET कोर) , 89 88 86 79 बाइट्स

  • थोड़ा अलग दृष्टिकोण के साथ सिर्फ 1 बाइट को बचाया।
  • forएस के सरलीकरण के साथ एक और 2 बाइट्स सहेजे गए ।
  • VisualMelon के अद्भुत गोल्फ कौशल के लिए 7 बाइट्स को बचाया।
a=>{for(int i=0,j,k;++i<a.Length;)for(k=a[i-1]-a[j=i]+1;--j>=0;)a[j]-=k>0?k:0;}

इसे ऑनलाइन आज़माएं!

पहले forसरणी के माध्यम से पुनरावृत्त होता है, फिर यह वेतन वृद्धि की गणना करता है और अंत में forयदि दूसरा iस्थान आवश्यक हो तो तत्वों को घटाता है ।

क्या किसी नए को वापस करने (अभी भी नियमों के अभ्यस्त) के बजाय मूल सरणी को संशोधित करना वैध है?


हां, मूल सरणी को संशोधित करना बिल्कुल ठीक है। :)
DJMcMayhem

4
@DJMcMayhem धन्यवाद, मुझे एक नया बनाने के लिए बहुत आलस्य महसूस हुआ। :)
चार्ली
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.