वर्गों की गणना करें


18

चुनौती

ओरिगामी (फोल्डिंग पेपर) कला का एक रचनात्मक रूप है। जहाँ तक मुझे पता है, ओरिगेमी का मास्टर वर्ग पेपर पसंद करता है। आइए शुरुआत से शुरू करें - एक आयताकार कागज को एक वर्ग एक में बदलें।

इसलिए कागज को वर्गों में विभाजित किया गया है। हम सबसे बड़े वर्ग को हटाते हैं जो मौजूदा आकार के साथ एक छोटा किनारा साझा करता है, चरण दर चरण (नीचे दी गई तस्वीर देखें)। और अगर एक चरण के बाद शेष भाग कम या बराबर है 0.001 * (area of the original paper), तो कागज को आगे विभाजित नहीं किया जा सकता है। यह संभव है कि कुछ भी आखिरी नहीं रहे।

आपका कार्य यह गणना करना है कि प्रक्रिया के दौरान कितने वर्ग बने हैं। अंतिम चरण में वर्ग जो कागज को विभाजित करने में असमर्थ बनाता है, को आउटपुट में गिना जाता है।

उदाहरण ( 1.350चौड़ाई / ऊंचाई का एक कागज ), आउटपुट 10 है:

टुकड़ा उदाहरण

इनपुट और आउटपुट

इनपुट: आयताकार कागज के लिए चौड़ाई / ऊंचाई अनुपात, से एक दशमलव (या डॉट के बिना एक पूर्णांक) 1.002करने के लिए 1.999का एक न्यूनतम कदम के साथ 0.001। आप अनुपात का वर्णन करने वाले किसी अन्य उचित प्रारूप का भी उपयोग कर सकते हैं। बस अपने उत्तर में इसका उल्लेख करें।

आउटपुट: वर्ग गणना, एक पूर्णांक।

उदाहरण I / O

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

1.002 => 251
1.003 => 223
1.004 => 189
1.005 => 161
1.006 => 140
1.007 => 124
1.008 => 111
1.009 => 100

सभी उत्तरों की सूची

@LuisMendo के लिए धन्यवाद, यहां उत्तरों का ग्राफ है।

ग्राफ

टिप्पणियों

  • यह एक कोड-गोल्फ है इसलिए सबसे छोटा कोड जीतता है
  • मानक खामियों पर ध्यान दें
  • यह तय करने की आपकी स्वतंत्रता है कि इनपुट और आउटपुट से कैसे निपटें लेकिन उन्हें मानक प्रतिबंधों का पालन करना चाहिए।

वैसे...

  • चुनौती के बारे में कुछ भी स्पष्ट न होने पर टिप्पणी करें
  • व्यक्तिगत रूप से मेरा सुझाव है कि यदि आप एक गोल्फ भाषा का उपयोग कर रहे हैं तो आपके उत्तर में एक स्पष्टीकरण होगा
  • @GregMartin के लिए धन्यवाद, चुनौती के लिए एक अच्छे गणितीय स्पष्टीकरण के लिए उसका उत्तर पढ़ें।

उदाहरण कोड

यहाँ C ++ कोड का एक ungolfed संस्करण है:

#include <iostream>
#include <utility>

int f (double m)
{
    double n = 1, k = 0.001;
    int cnt = 0;
    k *= m;                       // the target minimum size
    while(m*n >= k)
    {
        m -= n;                   // extract a square
        if(n > m)
            std::swap(n, m);      // keep m > n
        ++ cnt;
    }
    return cnt;
}

int main()
{
    double p;
    std::cin >> p;
    std::cout << f(p);
    return 0;
}

उदाहरण कोड में संबंधित सभी गणनाओं को 6 दशमलव अंकों की सटीकता की आवश्यकता होती है, जो इसमें शामिल है float


क्या अनुपात बनाने वाली दो संख्याओं को इनपुट के रूप में इस्तेमाल किया जा सकता है?
लुइस मेन्डो

@LuisMendo हाँ, अपनी इच्छा के रूप में।
कीउ गण

2
नीट चुनौती!
दोष

5
उत्तरों की सूची एक अच्छा ग्राफ
लुइस मेन्डो

1
@KeyuGan बेशक, आगे बढ़ो! मुझे बताएं कि क्या आपको किसी अन्य प्रारूप के साथ एक संस्करण की आवश्यकता है
लुइस मेंडो

जवाबों:


2

MATL , 19 बाइट्स

`SZ}y-htG/p1e-3>}x@

इनपुट एक सरणी है जिसमें मूल अनुपात को परिभाषित करने वाले दो नंबर होते हैं, जैसे कि [1, 1.009] । (यह आवश्यक नहीं है कि संख्याओं को क्रमबद्ध किया जाए या उनमें से कोई 1 हो।)

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

व्याख्या

`        % Do...while loop
  S      %   Sort array. Takes 1×2 array as input (implicit) the first time
  Z}     %   Split array into its 2 elements: first the minimum m, then the maximum M
  y      %   Duplicate m onto the top of the stack. The stack now contains m, M, m
  -      %   Subtract. The stack now contains m, M-m
  h      %   Concatenate into [m, M-m]. This is the remaining piece of paper
  t      %   Duplicate
  G/     %   Divide by input, element-wise
  p      %   Product of array. Gives ratio of current piece's area to initial area
  1e-3>  %   True if this ratio exceeds 1e-3. In that case the loop continues
}        % Finally (execute after last iteration, but still within the loop)
  x      %   Delete last piece of paper
  @      %   Push current loop counter. This is the result
         % End (implicit)
         % Display (implicit)

6

हास्केल , 71 70 65 63 62 61 58 56 बाइट्स

कुछ सरल सुधारों के लिए @xnor को धन्यवाद!

(n#m)e|e>n*m*1e3=0|n<m=m#n$e|d<-n-m=(d#m)e+1
n!m=n#m$n*m

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


यह लगता है m==nकि अंत में हो सकता है 1>0क्योंकि यह एकमात्र संभावना शेष है। या, शायद मामलों को यहाँ बाँधने के लिए पुनर्व्यवस्थित किया जा सकता है।
15

दरअसल, क्या समानता के मामले की जरूरत है? यदि n>mइसका विस्तार किया गया है n>=mऔर पहली जांच लिखी गई है e>m*n*1000, जो 1समानता के लिए देनी चाहिए ।
xnor

@xnor अच्छा विचार है, धन्यवाद!
निर्दोष

1
56 के लिए गार्ड के चारों ओर (n#m)e|e>n*m*1e3=0|n<m=m#n$e|d<-n-m=(d#m)e+1;n!m=n#m$n*m
घूमना

वाह, के d<-n-mरूप otherwiseमें वास्तव में साफ है का उपयोग !!!
११

4

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

f=(m,n=!(k=m/1e3,c=0))=>m*n<k?c:(c++,m-=n)<n?f(n,m):f(m,n)

परीक्षा


4

गणितज्ञ, गैर-गैर-प्रतिस्पर्धी (21 बाइट्स)

यह उत्तर गैर-प्रतिस्पर्धात्मक है क्योंकि यह पूछे गए वास्तविक प्रश्न का उत्तर नहीं देता है! लेकिन यह सवाल का एक प्रकार का जवाब देता है, और कुछ दिलचस्प गणित को उजागर करने का बहाना प्रदान करता है।

Tr@*ContinuedFraction

इनपुट के रूप में एक सकारात्मक परिमेय संख्या (जिसके अंश और भाजक मूल कागज के आयामों का प्रतिनिधित्व करते हैं) और एक सकारात्मक पूर्णांक लौटाता है। उदाहरण के लिए,Tr@*ContinuedFraction[1350/1000] रिटर्न 10। (ContinuedFraction सटीक मुद्दों के कारण फ्लोटिंग-पॉइंट नंबरों पर अलग-अलग कार्य करता है, यही कारण है कि इस संदर्भ में इनपुट के रूप में एक तर्कसंगत संख्या की आवश्यकता है।)

समस्या में वर्णित ज्यामितीय प्रक्रिया की एक दिलचस्प व्याख्या (एक आयत को बार-बार काटकर अलग करना) यह है कि यह सबसे बड़ा सामान्य विभाजक खोजने के लिए यूक्लिडियन एल्गोरिथ्म का कार्यान्वयन है! अनुपात के साथ प्रश्न में ही उदाहरण पर विचार करें1.35, जो आयामों (1350,1000) के साथ कागज का एक टुकड़ा होने से मॉडलिंग की जा सकती थी। हर बार एक वर्ग काट दिया जाता है, छोटी संख्या बड़ी संख्या से घटा दी जाती है; इसलिए इस उदाहरण में आयतों के आयाम (350,1000), तब (350,650), फिर (350,300), फिर (50,300), फिर (50,250) और (50,200) और (50,150) और (50,100) और (50) हैं। 50), और भी (50,0) एक बार जब हम अपने आप से आखिरी वर्ग निकाल लेते हैं। यह ठीक इसी प्रकार है कि यूक्लिडियन एल्गोरिथ्म संचालित होता है (विभाजन और बार-बार घटाव के बीच अंतर को मापता है), और वास्तव में हम देखते हैं कि 50 वास्तव में 1350 और 1000 का जीसीडी है।

आमतौर पर यूक्लिडियन एल्गोरिथ्म में, कोई इन मध्यवर्ती आयामों पर नज़र रखता है और घटाव की संख्या को घटाता है; हालाँकि, कोई भी वैकल्पिक रूप से रिकॉर्ड कर सकता है कि अंतर कम होने से पहले हमने कितनी बार एक नंबर को दूसरे से घटाया और हमें जो घटाना है उसे स्विच करना होगा। रिकॉर्डिंग की वह विधि एक परिमेय संख्या के निरंतर अंश है। (अपरिमेय संख्याओं के निरंतर अंश, जो कभी समाप्त नहीं होते हैं, सुपर कूल भी हैं, लेकिन यहां प्रासंगिक नहीं हैं।) उदाहरण के लिए, उदाहरण में, 1350/1000 में, हमने 1000 1समय घटाया , फिर 3502 बार, फिर 300 1समय, फिर 50 6बार; इसलिए 1350/1000 का निरंतर अंश है {1,2,1,6}। गणितीय रूप से, हमने 1350/1000 को 1+ 1 / ( ) के रूप में फिर से लिखा है , जिसे आप सत्यापित कर सकते हैं।2 + 1 / ( 1+ 1 /) के6

इस समस्या के लिए, यदि आप रोक नहीं पाते हैं जब वर्ग एक निश्चित सीमा से छोटा हो जाता है, लेकिन बस रुकने से पहले सभी बारीकियों को गिनें, तो वर्गों की कुल संख्या घटाव की कुल संख्या के बराबर होती है, जो कहना है जारी अंश में सभी पूर्णांकों का योग — और यह वही है जो कार्यों की संरचना की Tr@*ContinuedFractionगणना करता है! (दिए गए उदाहरण 1.35 के लिए, यह उत्तर मिलता है कि ओपी इच्छाओं को पूरा करता है, क्योंकि अंतिम वर्ग काफी बड़ा है कि सभी वर्गों की गिनती की गई थी। लेकिन Tr@*ContinuedFraction[1001/1000], उदाहरण के लिए, पैदावार 1001, क्योंकि यह एक विशाल वर्ग और छोटे 1xx वर्गों के सभी 1000 की गिनती करता है। ।)


1
हालांकि यह वास्तव में दिलचस्प है, गैर-प्रतिस्पर्धी लेबल उन भाषाओं के लिए आरक्षित है जो चुनौती से नए हैं । स्वतंत्र रूप से, सभी उत्तरों को चुनौती को हल करने की आवश्यकता है। इसलिए, इस उत्तर को वास्तव में हटा दिया जाना चाहिए। क्या आप निरंतर भिन्न सूची से पुनर्निर्माण कर पाएंगे, जहां इसे काट दिया जाए ताकि इसे समान रूप से दिलचस्प लेकिन मान्य समाधान में बदल दिया जा सके?
मार्टिन एंडर

1
इस उत्तर को लिखते समय मुझे खरोंच पड़ने की मानसिक खुजली थी, लेकिन मैं मानता हूं कि यह सामुदायिक मानकों के अनुसार डिलीट-योग्य उत्तर है। (आपकी कोमल अभी तक सटीक प्रतिक्रिया के लिए धन्यवाद!) अगर टीपीटीबी को 24 घंटे के लिए इसके विलोपन में देरी की तरह लगता है, तो मैं सही उत्तर देने के लिए दृष्टिकोण की शिकायत करने में सक्षम हो सकता हूं ... यदि नहीं, तो हटा दें और कोई कठिन भावनाओं को नहीं।
ग्रेग मार्टिन

3

गणितज्ञ, ६४ ५३ बाइट्स

({t=1,#}//.{a_,b_}/;1000a*b>#:>Sort@{++t;a,b-a};t-1)&

एक अनिवार्य (सी-शैली) समाधान बिल्कुल समान लंबाई है:

(For[t=a=1;b=#,1000a*b>#,If[a>b,a-=b,b-=a];++t];t-1)&

2

सी (जीसीसी / क्लैंग), 61 59 बाइट्स

c,k;f(m,n){for(k=m*n;m*n/k;m>n?(m-=n):(n-=m))++c;return c;}

इनपुट बिना डॉट के दो पूर्णांक (चौड़ाई और ऊंचाई) है, जैसे कि f(1999,1000)

मुझे आशा है कि कोई 58 बाइट क्लब में एक बाइट को धक्का देकर बचा सकता है। ;)


कोष्ठकों को हटाने का सुझावm-=n
छत

1

सी, 59 बाइट्स

s,a,n=1e3;C(m){for(a=m;m*n>a;s++)m>n?m-=n:(n-=m);return s;}

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

इनपुट एक पूर्णांक है जो हज़ारवें में चौड़ाई / ऊंचाई अनुपात है (उदाहरण के लिए 1.002: 1 के लिए 1002)।

अनप्लग्ड संस्करण

int C(int m)
{
    int n = 1000;
    int a = m;
    int s = 0;

    while (m * n > a)
    {
        if (m > n)
            m -= n;
        else
            n -= m;

        s++;
    }

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