See the original problem on HackerRank.
        
        Solutions
A tradeoff of this problem is about using a temporary array or not. In the
latter case, the steps to do are simpler because we can just copy the two parts
the array: all the elements before the rotation point and then all the element
after.
Here is a Java implementation:
|  1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
 | public static int[] rotateArray(int[] arr, int d)
{
    int n = arr.length;
    int[] rotated = new int[n];
    // Copy segments of shifted elements to rotated array:
    System.arraycopy(arr, d, rotated, 0, n - d);
    System.arraycopy(arr, 0, rotated, n - d, d);
    return rotated;
}
 | 
 
Here is an interesting solution using Linq in C#, by Emanuele
Prato:
| 1
2
3
4
5
6
 | static int[] leftRotation(int[] a, int d)
{
    int[] array1 = a.Take(d).Reverse().ToArray();
    int[] array2 = a.Skip(d).Take(a.Length - d + 1).Reverse().ToArray();
    return array1.Concat(array2).Reverse().ToArray();
}
 | 
 
Doing the roation in-place is more challenging.
First of all, you may have noticed that “cheating” is possible by allocating the
final array and then reading the elements in the final positions - by Roberto
Melis:
|  1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
 | vector<int> values(n);
// reading to 'd'
for (int i = 0; i < d; ++i)
{
    cin >> values[n-d+i];
}
// reading from 'd' to the end
for (int i = 0; i < n-d; ++i)
{
    cin >> values[i];
}
for (auto & v : values)
{
    cout << v << " ";
}
 | 
 
The problem of rotation can be solved by doing a “reverse” operation three
times. Here is the core part, by Roberto
Melis:
|  1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
 | vector<int> values(n);
copy_n(istream_iterator<int>(cin), n, begin(values));
auto swap = [&values](int from, int to)
{
    for (int i = from; i < from+(to-from)/2; ++i)
        std::swap(values[i], values[to-1-(i-from)]);
};
swap(0, d);
swap(d, n);
swap(0, n);
copy(begin(values), end(values), ostream_iterator<int>(cout, " "));
 | 
 
swap can be rewritten in terms of std::reverse:
| 1
2
3
4
5
6
7
8
 | vector<int> values(n);
copy_n(istream_iterator<int>(cin), n, begin(values));
reverse(begin(v), begin(v)+d);
reverse(begin(v)+d, end(v));
reverse(begin(v), end(v));
copy(begin(values), end(values), ostream_iterator<int>(cout, " "));
 | 
 
In Haskell:
| 1
 | leftRotation d arr = reverse ( ( reverse ( take d arr ) ) ++ ( drop d arr ) )
 | 
 
Actually, in C++ we can replace the whole logic with std::rotate:
| 1
2
3
4
5
6
7
8
 | int d;
cin >> d >> d;
vector<int> v{istream_iterator<int>(cin), istream_iterator<int>()};
if (d != v.size())
{
    rotate(begin(v), begin(v)+d, end(v));
}
copy(begin(v), end(v), ostream_iterator<int>(cout, " "));
 | 
 
If we can stream to the output without using a function returning an array,
we can just stream the two chunks at ranges [d, n - d) and [0, d).
|  1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
 | #include <iostream>
#include <vector>
#include <iterator>
#include <algorithm>
using namespace std;
int main() {
    int n, d;
    cin >> n >> d;
    vector<int> values(n);
    copy_n(istream_iterator<int>(cin), n, begin(values));
    copy_n(begin(values) + d, n - d, ostream_iterator<int>(cout, " "));
    copy_n(begin(values)    , d    , ostream_iterator<int>(cout, " "));
}
 | 
 
If data is not an array but a linked list (as std::list) we can easily
change list internal pointers with slice. No elements are copied in this case.
|  1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
 | #include <iostream>
#include <list>
#include <iterator>
#include <algorithm>
using namespace std;
void rotate_left(list<int>& v, int d) {
    v.splice(v.begin(), v, next(v.begin(), d), v.end());
}
int main() {
    int n, d;
    cin >> n >> d;
    list<int> v;
    copy_n(istream_iterator<int>(cin), n, back_inserter(v));
    rotate_left(v, d);
    copy(begin(v), end(v), ostream_iterator<int>(cout, " "));
}
 | 
 
In Haskell, the solution is very terse: just concatenates two list, one where d
elements have been dropped, and one where d elements have been taken.
| 1
2
3
4
5
6
 | leftRotation :: Int -> [Int] -> [Int]
leftRotation d arr = drop d arr ++ take d arr
main = do
  (d:arr) <- ( fmap read ) . drop 1 . words <$> getContents
  putStr $ unwords $ fmap show $ leftRotation d arr
 | 
 
Due to lazyness of Haskell, the list arr is not copyied, but streamed directly
to the IO. A similar solution may be written in C++ like that:
|  1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
 | #include <iostream>
#include <list>
#include <iterator>
#include <algorithm>
using namespace std;
void drop(std::ostream& os, const list<int>& v, int d) {
    copy(next(begin(v), d), end(v), ostream_iterator<int>(cout, " "));
}
void take(std::ostream& os, const list<int>& v, int d) {
    copy(begin(v), next(begin(v), d), ostream_iterator<int>(cout, " "));
}
int main() {
    int n, d;
    cin >> n >> d;
    list<int> v;
    copy_n(istream_iterator<int>(cin), n, back_inserter(v));
    drop(cout, v, d);
    take(cout, v, d);
}
 | 
 
Anyway, this problem is instructive. We can try rolling our own implementation
of array rotation or understand that it’s possible to use three calls to
reverse.