ও (এন) অ্যালগরিদম [বন্ধ] সহ একটি পূর্ণসংখ্যার অ্যারে ঘোরান


10

কোনও ফাংশন লিখুন যা প্রদত্ত সংখ্যা কে দ্বারা একটি পূর্ণসংখ্য অ্যারে ঘোরায়। শেষের দিকের k উপাদানগুলি অ্যারের শুরুতে চলে যেতে হবে এবং অন্যান্য সমস্ত উপাদান স্থান তৈরি করতে ডানদিকে যেতে হবে।

ঘূর্ণনটি জায়গায় জায়গায় করা উচিত।

অ্যালগরিদম O (n) এর চেয়ে বেশি চলবে না, যেখানে n অ্যারের আকার।

এছাড়াও অপারেশন সঞ্চালনের জন্য একটি ধ্রুবক মেমরি ব্যবহার করা উচিত।

উদাহরণ স্বরূপ,

অ্যারে উপাদানগুলি অ্যারে = {1, 2, 3, 4, 5, 6, 7, 8, 9 with দিয়ে শুরু করা হলে

ঘোরানো (আরার, 3) এর ফলে উপাদানগুলি {7, 8, 9, 1, 2, 3, 4, 5, 6 result হয়ে যাবে

ঘোরান (এআর, 6) ফলাফল {4, 5, 6, 7, 8, 9, 1, 2, 3}


1
এখানে ধ্রুব স্মৃতি বলতে কী বোঝায়? অবশ্যই এর ( O) মেমরির ব্যবহার অসম্ভব করে প্রসেস করা হচ্ছে অ্যারে সংরক্ষণ করার জন্য কমপক্ষে কমপক্ষে ও (এন) মেমরির প্রয়োজন ।
অ্যাডহক গার্ফ হান্টার

2
আমি এই প্রশ্নটিকে অফ-টপিক হিসাবে বন্ধ করতে ভোট দিচ্ছি কারণ উদ্দেশ্যমূলক প্রাথমিক বিজয়ী মানদণ্ড ব্যতীত প্রশ্নগুলি অফ-টপিক, কারণ কোন প্রবেশিকাটি জিততে হবে তা নির্বিচারে সিদ্ধান্ত নেওয়া অসম্ভব করে তোলে। একেবারে কোনও কারণ নেই যে এটি জনপ্রিয়তার প্রতিযোগিতা হওয়া উচিত।
জেমস

ভোট বন্ধ। থেকে জনপ্রিয়তা-প্রতিযোগিতা উইকি ( এখানে ), "কি গুরুত্বপূর্ণ অংশে কাজ করার সিদ্ধান্ত নেন করার সমাগম স্বাধীনতা দেয় এবং এই স্বাধীনতা তারা ব্যবহার করে সেটি incentivizes।" আমি মনে করি না যে চ্যালেঞ্জটি কোনও অ্যালগরিদমকে উন্মুক্ত রেখে দেওয়া যেমন সাধারণ চ্যালেঞ্জের জন্য সৃজনশীলতাকে উত্সাহিত করা হিসাবে গণ্য করা হয়, অন্ততপক্ষে এটি পপকন হিসাবে কাজ করে না not এটি কোড-গল্ফ চ্যালেঞ্জ হিসাবে আরও উপযুক্ত ।
mbomb007

উত্তর:


18

সি (104)

void reverse(int* a, int* b)
{
    while (--b > a) {
        *b ^= *a;
        *a ^= *b;
        *b ^= *a;
        ++a;
    }
}

void rotate(int *arr, int s_arr, int by)
{
    reverse(arr, arr+s_arr);
    reverse(arr, arr+by);
    reverse(arr+by, arr+s_arr);
}

minified:

v(int*a,int*b){while(--b>a){*b^=*a;*a^=*b;*b^=*a++;}}r(int*a,int s,int y){v(a,a+s);v(a,a+y);v(a+y,a+s);}

4
আপনার কিছুক্ষণ লুপ শর্তটি লিখে রাখা উচিত ছিলa <-- b
justhalf

একটি সময় ব্যবহৃত হত যখন সি প্রোগ্রামগুলি জনপ্রিয়তা প্রতিযোগিতা
জিতত

তুমিই শ্রেষ্ঠ! কত মার্জিত এবং অপ্টিমাইজড .. আপনি কি বিট অ্যারে দিয়ে এটি করতে পারেন?

9

এপিএল (4)

¯A⌽B
  • A ঘুরানোর জায়গাগুলির সংখ্যা
  • বি ঘোরানো অ্যারের নাম

আমি নিশ্চিত নই যে এপিএল আসলে এটির প্রয়োজন হয়েছিল, তবে বাস্তবায়নে আমি দেখেছি (অভ্যন্তরীণ) এটি আনুপাতিক সময় Aএবং ধ্রুবক স্মৃতিতে সময় নেবে ।


+1 যদি এটি গল্ফ হয় :)
গ্লেন টিটেলবাম

যদিও এটি এটি জায়গায় না করে।
মেরিনাস

@ মারিনাস: আমি দেখেছি এমন বাস্তবায়নে এটি অবশ্যই কাজ করে।
জেরি কফিন

এটি কিভাবে একটি ফাংশন? হতে পারে {⍵⌽⍨-⍺}বা {⌽⍺⌽⌽⍵}। NARS2000 এ এটি মার্জিতভাবে হিসাবে লিখিত হতে পারে ⌽⍢⌽
Adám

5

কলিনের ধারণার একটি দীর্ঘ বায়ুযুক্ত সি সংস্করণ এখানে।

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int gcd(int a, int b) {
  int t;
  if (a < b) {
    t = b; b = a; a = t;
  }
  while (b != 0) {
    t = a%b;
    a = b;
    b = t;
  }
  return a;
}

double arr[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12};
int s_arr = sizeof(arr)/sizeof(double);

/* We assume 1 <= by < s_arr */
void rotate(double *arr, int s_arr, int by) {
  int i, j, f;
  int g = gcd(s_arr,by);
  int n = s_arr/g;
  double t_in, t_out;

  for (i=0; i<g; i++) {
    f = i;
    t_in = arr[f + s_arr - by];
    for (j=0; j<n; j++) {
      t_out = arr[f];
      arr[f] = t_in;
      f = (f + by) % s_arr;
      t_in = t_out;
    }
  }
}

void print_arr(double *arr, int s_arr) {
  int i;
  for (i=0; i<s_arr; i++) printf("%g ",arr[i]);
  puts("");
}

int main() {
  double *temp_arr = malloc(sizeof(arr));
  int i;

  for (i=1; i<s_arr; i++) {
    memcpy(temp_arr, arr, sizeof(arr));
    rotate(temp_arr, s_arr, i);
    print_arr(temp_arr, s_arr);
  }
}

এটি ধ্রুবক স্মৃতি সমাধানের মতো দেখায় না, তাই না?
মাইক্রোবিয়ান

হ্যাঁ এটি একটি ধ্রুবক স্মৃতি সমাধান। "মলযুক্ত" জিনিসগুলি অ্যারের অস্থায়ী অনুলিপি যাতে আমি এটিতে বারবার আসল তথ্য অনুলিপি করতে পারি, যাতে আমি বিভিন্ন ঘূর্ণনের পরিমাণ পরীক্ষা করতে পারি।
স্টিফেন মন্টগোমেরি-স্মিথ

আসল ঘোরান কীটি হ'ল ফাংশনটি "ঘোরান" is এটিতে পাঁচটি পূর্ণসংখ্যা এবং দুটি ডাবল ব্যবহার করা হয়েছে। এটি একটি ফাংশনকে "জিসিডি "ও বলে যা একটি পূর্ণসংখ্যার ব্যবহার করে এবং বেশিরভাগ ও (লগ (এন)) অপারেশন ব্যবহার করে।
স্টিফেন মন্টগোমেরি-স্মিথ

বুঝেছি. আমি আপনার উত্তর upp।
মাইক্রোবিয়ান

@ স্টিফেনমন্টগোমেরি-স্মিথ - এই O(log(n))কার্যক্রমগুলি কেমন চলছে। এ লুক by1 হচ্ছে আপনার `ঞ 'লুপ s_arr / G অথবা এন - এই হে (ঢ) অপারেশন হয়
গ্লেন Teitelbaum

3

সি

মানদণ্ডটি কী তা নিশ্চিত নন, তবে যেহেতু আমি অ্যালগরিদমের সাথে মজা করেছি, তাই আমার প্রবেশ এখানে রয়েছে:

void rotate(int* b, int size, int shift)
{
    int *done;
    int *p;
    int i;
    int saved;
    int c;

    p = b;
    done = p;
    saved = *p;
    for (i = 0; i < size; ++i) {
        c = saved;
        p += shift;
        if (p >= b+size) p -= size;
        saved = *p;
        *p = c;
        if (p == done) {
            p += 1;
            done = p;
            saved = *p;
        }
    }
}

আমি এটি একটি ভাল পরিমাপ জন্য গল্ফ করব; 126 বাইট, আরও ছোট করা যেতে পারে:

void r(int*b,int s,int n){int*d,*p,i,t,c;d=p=b;t=*p;for(i=0;i<s;++i){c=t;p+=n;if(p>=b+s)p-=s;t=*p;*p=c;if(p==d){d=++p;t=*p;}}}

3

আমি এখানে অনেকগুলি সি ++ সলিউশন দেখতে পাচ্ছি না, তাই আমি অনুভব করেছি যে আমি এটির চেষ্টা করব কারণ এটি অক্ষর গণনা করে না।

এটি সত্য "ইন-প্লেস" রোটেশন, সুতরাং 0 অতিরিক্ত স্থান ব্যবহার করে (প্রযুক্তিগতভাবে অদলবদল এবং 3 ইনট বাদে) এবং যেহেতু লুপটি হ'ল এন, তাই ও (এন) জটিলতাও পূরণ করে।

template <class T, size_t N>
void rot(std::array<T,N>& x, int shift)
{
        size_t base=0;
        size_t cur=0; 
        for (int i = 0; i < N; ++i)
        {
                cur=(cur+shift)%N; // figure out where we are going
                if (cur==base)     // exact multiple so we have to hit the mods when we wrap
                {
                        cur++;
                        base++;
                }
                std::swap(x.at(base), x.at(cur)); // use x[base] as holding area
        }
}

দ্রষ্টব্য: আমি উদ্দেশ্যমূলকভাবে ব্যবহার করিনি std::rotateকারণ এই ধরণের উদ্দেশ্যটি হেরে যায়
গ্লেন টাইটেলবাম

2

যদি আপনি ঘুরার প্রতিটি সম্ভাব্য চক্র প্রতিটি ঘটিত করে নিন (এর মধ্যে জিসিডি (এন, লেন (এআর)) থাকে তবে আপনার কেবল একটি অ্যারের উপাদানটির একটি অস্থায়ী অনুলিপি এবং কয়েকটি রাষ্ট্রীয় ভেরিয়েবলের প্রয়োজন। পাইথনে এটির মতো:

from fractions import gcd

def rotate(arr, n):
    total = len(arr)
    cycles = gcd(n, total)
    for start in range(0, cycles):
        cycle = [i % total for i in range(start, abs(n * total) / cycles, n)]
        stash = arr[cycle[-1]]
        for j in reversed(range(1, len(cycle))):
            arr[cycle[j]] = arr[cycle[j - 1]]
        arr[cycle[0]] = stash

1
আমি মনে করি আপনার সঠিক ধারণা আছে তবে আপনার cycleপরিবর্তনশীলটি অ-ধ্রুব আকারের। যাওয়ার সাথে সাথে আপনাকে এই অ্যারেটি তৈরি করতে হবে।
কীথ র্যান্ডাল

2

সি (১৩7 টি অক্ষর)

#include <stdio.h>

void rotate(int * array, int n, int k) {
    int todo = (1<<n+1)-1;
    int i = 0, j;
    int tmp = array[0];

    while (todo) {
        if (todo & 1<<i) {
            j = (i-k+n)%n;
            array[i] = todo & 1<<j ? array[j] : tmp;
            todo -= 1<<i;
            i = j;
        } else tmp = array[++i];
    }
}

int main() {
    int a[] = {1,2,3,4,5,6,7,8,9};
    rotate(a, 9, 4);
    for (int i=0; i<9;i++) printf("%d ", a[i]);
    printf("\n");
}

ফাংশনটি rotate137 টি অক্ষরে মাইন করা হয়েছে:

void r(int*a,int n,int k){int m=(1<<n+1)-1,i=0,j,t=a[0];while(m)if(m&1<<i){j=(i-k+n)%n;a[i]=(m&1<<j)?a[j]:t;m-=1<<i;i=j;}else t=a[++i];}

2

ঘূর্ণনযোগ্য অ্যারেগুলির জন্য কারখানার একটি বিল্ট-ইন টাইপ রয়েছে <circular>, সুতরাং এটি আসলে একটি ও (1) অপারেশন:

: rotate ( circ n -- )
    neg swap change-circular-start ;

IN: 1 9 [a,b] <circular> dup 6 rotate >array .
{ 4 5 6 7 8 9 1 2 3 }
IN: 1 9 [a,b] <circular> dup 3 rotate >array .
{ 7 8 9 1 2 3 4 5 6 }

বেন ভয়েগের চিত্তাকর্ষক সি সমাধানের তুলনায় কম চিটটি ফ্যাক্টর:

: rotate ( n s -- ) 
    reverse! swap cut-slice [ reverse! ] bi@ 2drop ;

IN: 7 V{ 0 1 2 3 4 5 6 7 8 9 } [ rotate ] keep .
V{ 3 4 5 6 7 8 9 0 1 2 }

2

জাভাস্ক্রিপ্ট 45

যাইহোক গল্ফের জন্য গিয়েছিলাম কারণ আমি গল্ফ পছন্দ করি। এটি সর্বাধিক ও (এন) যতক্ষণ tনা অ্যারের আকারের = = আকারে থাকে।

function r(o,t){for(;t--;)o.unshift(o.pop())}

tও (এন) এর যে কোনও অনুপাত হ্যান্ডেল করতে নিম্নলিখিতটি ব্যবহার করা যেতে পারে (58 টি চরিত্রের মধ্যে ওজন):

function r(o,t){for(i=t%o.length;i--;)o.unshift(o.pop())}

ফিরে আসে না, জায়গায় অ্যারে সম্পাদনা করে।


1
+1 এর জন্যr(o,t) => rot
কনার ও'ব্রায়ান

1

বিদ্রোহ - 22

/_(( \d+)+)( \d+)/$3$1

ইনপুট: কে _একটি অঙ্ক হিসাবে অখণ্ড পূর্ণসংখ্যার হিসাবে প্রকাশিত হয় , তারপরে একটি স্থান এবং তারপরে একটি স্পেস-বিস্মৃত পূর্ণসংখ্যার অ্যারে।

আউটপুট: একটি স্থান, তারপরে অ্যারে ঘোরানো।

উদাহরণ:

___ 1 2 3 4 5/_(( \d+)+)( \d+)/$3$1

চূড়ান্ত অবস্থা:

 3 4 5 1 2

ব্যাখ্যা:

প্রতিটি পুনরাবৃত্তিতে এটি এক _এবং একটি অ্যারের [array] + tailসাথে প্রতিস্থাপন করে tail + [array]

উদাহরণ:

___ 1 2 3 4 5
__ 5 1 2 3 4
_ 4 5 1 2 3
 3 4 5 1 2

আমি মনে করি না এটি ও (এন)। একটি অ্যারের অনুলিপি করা হয় O(n)এবং আপনি সেই nসময়টি করেন।
বেন ভয়েগট

1

জাভা

public static void rotate(int[] arr, int by) {
    int n = arr.length;
    int i = 0;
    int j = 0;
    while (i < n) {
        int k = j;
        int value = arr[k];
        do {
            k = (k + by) % n;
            int tmp = arr[k];
            arr[k] = value;
            value = tmp;
            i++;
        } while (k != j);
        j++;
    }
}

এখানে ডেমো ।

Minified জাভাস্ক্রিপ্ট, 114 :

function rotate(e,r){n=e.length;i=0;j=0;while(i<n){k=j;v=e[k];do{k=(k+r)%n;t=e[k];e[k]=v;v=t;i++}while(k!=j);j++}}

1

Haskell,

এটি আসলে θ (এন), কারণ বিভাজনটি is (কে) এবং জোড় θ (এন কে)। যদিও স্মৃতি সম্পর্কে নিশ্চিত নয়।

rotate 0 xs = xs
rotate n xs | n >= length xs = rotate (n`mod`(length xs)) xs
            | otherwise = rotate' n xs

rotate' n xs = let (xh,xt) = splitAt n xs in xt++xh

1

পাইথন ঘ

from fractions import gcd
def rotatelist(arr, m):
    n = len(arr)
    m = (-m) % n # Delete this line to change rotation direction
    for i0 in range(gcd(m, n)):
        temp = arr[i0]
        i, j = i0, (i0 + m) % n
        while j != i0:
            arr[i] = arr[j]
            i, j = j, (j + m) % n
        arr[i] = temp

অবিচ্ছিন্ন মেমরি
ও (এন) সময়ের জটিলতা


0

পাইথন

def rotate(a, n): a[:n], a[n:] = a[-n:], a[:-n] 

এটি কি ধ্রুব স্মৃতি ব্যবহার করবে?
SztupY

হুম ... নিশ্চিত না
ম্যাডিসন মে

এটি একটি ধ্রুবক মেমরি অপারেশন নয়।
মাইক্রোবিয়ান

এই যা। শুভ কল ...
ম্যাডিসন মে

0

পাইথন

   import copy
    def rotate(a, r):
        c=copy.copy(a);b=[]
        for i in range(len(a)-r):   b.append(a[r+i]);c.pop();return b+c

অ্যারে অনুলিপি করা ধ্রুব স্থান নয়। @ ম্যাডিসনময়ের উত্তরটি অনেক কম অক্ষরের সাথে এই কোডটির মতো মূলত একই জিনিস করে।
ব্ল্যাকঙ্কহাত

0

vb.net ও (এন) (কনস্ট্যান্ট মেমরি নয়)

Function Rotate(Of T)(a() As T, r As Integer ) As T()     
  Dim p = a.Length-r
  Return a.Skip(p).Concat(a.Take(p)).ToArray
End Function

0

চুনি

def rotate(arr, n)
  arr.tap{ (n % arr.size).times { arr.unshift(arr.pop) } }  
end

0

সি (118)

সম্ভবত কিছু নির্দিষ্টকরণের জন্য কিছুটা লেনিয়েন্ট ছিল। আনুপাতিক মেমরি ব্যবহার করে shift % length। নেতিবাচক শিফ্ট মানটি পাস করা হলে বিপরীত দিকে ঘোরাতে সক্ষম।

r(int *a,int l,int s){s=s%l<0?s%l+l:s%l;int *t=malloc(4*s);memcpy(t,a+l-s,4*s);memcpy(a+s,a,4*(l-s));memcpy(a,t,4*s);}

0

পাইথন 2, 57

def rotate(l,n):
 return l[len(l)-n:len(l)]+l[0:len(l)-n]

যদি l[-n:len(l)-n]আমি কেবল এটির মতো কাজ করতাম। এটি কেবল []কোনও কারণে ফিরে আসে ।


0
def r(a,n): return a[n:]+a[:n]

কেউ দয়া করে এটি পরীক্ষা করে প্রয়োজনীয়তাগুলি পূরণ করে কিনা তা পরীক্ষা করতে পারেন? আমি মনে করি এটি করে তবে এটি আমি সিএস (এখনও) অধ্যয়ন করি নি।


0

সি ++, 136

template<int N>void rotate(int(&a)[N],int k){auto r=[](int*b,int*e){for(int t;--e>b;t=*b,*b++=*e,*e=t);};r(a,a+k);r(a+k,a+N);r(a,a+N);}

0

জাভা

প্রথম কে উপাদানগুলির সাথে শেষ কে উপাদানগুলিকে অদলবদল করুন এবং তারপরে অবশিষ্ট উপাদানগুলি কে দ্বারা আবর্তিত করুন। আপনার শেষে যখন k এর চেয়ে কম উপাদান অবশিষ্ট থাকবে তখন এগুলিকে কে% সংখ্যা অনুসারে রেখে দিন by আমি মনে করি না উপরের কেউ এই পদ্ধতি গ্রহণ করেছে। প্রতিটি উপাদানের জন্য ঠিক একটি সোয়াপ অপারেশন সম্পাদন করে, সবকিছু জায়গায় করে।

public void rotate(int[] nums, int k) {
    k = k % nums.length; // If k > n, reformulate
    rotate(nums, 0, k);
}

private void rotate(int[] nums, int start, int k) {
    if (k > 0) {
        if (nums.length - start > k) { 
            for (int i = 0; i < k; i++) {
                int end = nums.length - k + i;
                int temp = nums[start + i];
                nums[start + i] = nums[end];
                nums[end] = temp;
            }
            rotate(nums, start + k, k); 
        } else {
            rotate(nums, start, k % (nums.length - start)); 
        }
    }
}

0

পার্ল 5 , 42 বাইট

sub r{$a=pop;map{unshift@$a,pop@$a}1..pop}

এটি অনলাইন চেষ্টা করুন!

প্রথম প্যারামিটার হিসাবে ঘুরতে সুব্রুটাইন দূরত্ব এবং দ্বিতীয় হিসাবে অ্যারের রেফারেন্স নেয়। সঞ্চালনের সময়টি ঘূর্ণনের দূরত্বের ভিত্তিতে স্থির থাকে। অ্যারের আকার রান সময়কে প্রভাবিত করে না। অ্যারের স্থান থেকে ডান দিক থেকে একটি উপাদান সরিয়ে এবং বাম দিকে রেখে পরিবর্তিত হয়।

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.