130

I know that Java has a function System.arraycopy(); to copy an array. I was wondering if there is a function in C or C++ to copy an array. I was only able to find implementations to copy an array by using for loops, pointers, etc. But is there a library function that I can use to copy an array?

user16217248
  • 3,119
  • 19
  • 19
  • 37
J L
  • 2,157
  • 3
  • 16
  • 15
  • 8
    `man memmove` and `man memcpy` –  Apr 22 '13 at 01:06
  • 34
    Don't use `memcpy`, use `std::copy`. If your type has a meaningful copy constructor then `memcpy` will do the wrong thing. – Ed S. Apr 22 '13 at 01:17
  • 12
    Are you actually trying to learn C and C++ at the same time? They are very different languages. – Ferruccio Apr 22 '13 at 01:21
  • 1
    Well I learned little bit of C and now I recently started learning C++. From what I read from an online resource, I thought C++ is just a language with a lot of additional features to C language. – J L Apr 22 '13 at 01:27
  • @JL The two languages have evolved along different, out-of-sync paths. – autistic Apr 22 '13 at 02:10
  • @JL Consider implicit `void *` conversion, in C: `char *foo = malloc(0);` fails in C++, but works in C. VLAs are a feature added by C99 that aren't in C++. Likewise for flexible array members. Even the modulo operator isn't guaranteed to work the same in C++ as it does in C. – autistic Apr 22 '13 at 02:12
  • 1
    Also see [Why declare a struct that only contains an array in C?](http://stackoverflow.com/questions/6966570/why-declare-a-struct-that-only-contains-an-array-in-c) – Bo Persson Apr 22 '13 at 07:22
  • 9
    I'm saying this because no one has mentioned it before: In C++ you should use std::vector in almost all cases. There are cases where other containers are usefull too, but i most cases std::vector will be the best option. Don't use raw arrays in C++ and try to avoid std::array unless neccessary. – Skalli Apr 22 '13 at 14:27
  • 4
    Pick C or C++. They're very distinct. – MD XF Dec 06 '16 at 23:18

13 Answers13

191

Since you asked for a C++ solution...

#include <algorithm>
#include <iterator>

const int arr_size = 10;
some_type src[arr_size];
// ...
some_type dest[arr_size];
std::copy(std::begin(src), std::end(src), std::begin(dest));
Community
  • 1
  • 1
Ed S.
  • 122,712
  • 22
  • 185
  • 265
  • 4
    erreur: ‘begin’ is not a member of ‘std’ – David 天宇 Wong Sep 01 '14 at 14:35
  • 27
    @David天宇Wong: You're using an old compiler or you didn't include the header. It's in `` – Ed S. Sep 01 '14 at 17:54
  • 11
    Maybe you should say which includes you need. Is copy in `` ? – Jerry Jeremiah Dec 06 '16 at 23:13
  • 1
    @JerryJeremiah: I could, and you could always just google "std::copy" – Ed S. Dec 07 '16 at 19:45
  • 24
    I only ask because if you had to explain that std::begin was in that means people are not googling std::begin to find out what header it is in so they are unlikely to google std::copy for the same reason. It makes a better answer if nobody has to ask stuff that is only answered in comments. Maybe I should have just edited the answer instead of prompting you to do it. – Jerry Jeremiah Dec 08 '16 at 00:56
  • 6
    you can change begin(src) into src and end(src) into src+arr_size – Calvin Nov 10 '18 at 15:57
  • 1
    Here can be more simple like this, `copy(src,src+n,dest);` There, n is the array size. – nafischonchol Aug 24 '21 at 15:37
  • @EdS.@JerryJeremiah I did not include neither `` nor `` but still works. I don't know why... – Grace May 09 '23 at 08:45
110

Since C++11, you can copy arrays directly with std::array:

#include <array>
std::array<int, 4> A = {10, 20, 30, 40};
std::array<int, 4> B = A; // Copy array A into array B
Grace
  • 876
  • 1
  • 11
  • 21
taocp
  • 23,276
  • 10
  • 49
  • 62
  • @XAleXOwnZX: The same you would any other type that supports copy assignment. `B = A`. – swalog Mar 18 '15 at 14:11
  • 2
    I think the function is copy A's memory address to B. If I try to copy A's item values to B without changing B's memory address. How can I do that? – Aaron Lee Apr 26 '17 at 10:38
  • @Aaron_Lee: I've just tested it, and it genuinely copies the elements into an array in a separate memory location. The array class evidently has its own overload for the assignment operator. – Dave Rove Oct 21 '19 at 10:03
  • 14
    You guys realize that no assignment operators appeared in those two lines of code, right? That's the copy constructor that is being called even though the notation looks like the assignment operator. – Albino Cordeiro Nov 20 '19 at 22:18
105

As others have mentioned, in C you would use memcpy. Note however that this does a raw memory copy, so if your data structures have pointer to themselves or to each other, the pointers in the copy will still point to the original objects.

In C++ you can also use memcpy if your array members are POD (that is, essentially types which you could also have used unchanged in C), but in general, memcpy will not be allowed. As others mentioned, the function to use is std::copy.

Having said that, in C++ you rarely should use raw arrays. Instead you should either use one of the standard containers (std::vector is the closest to a built-in array, and also I think the closest to Java arrays — closer than plain C++ arrays, indeed —, but std::deque or std::list may be more appropriate in some cases) or, if you use C++11, std::array which is very close to built-in arrays, but with value semantics like other C++ types. All the types I mentioned here can be copied by assignment or copy construction. Moreover, you can "cross-copy" from opne to another (and even from a built-in array) using iterator syntax.

This gives an overview of the possibilities (I assume all relevant headers have been included):

#include <vector>
int main()
{
  // This works in C and C++
  int a[] = { 1, 2, 3, 4 };
  int b[4];
  memcpy(b, a, 4*sizeof(int)); // int is a POD

  // This is the preferred method to copy raw arrays in C++ and works with all types that can be copied:
  std::copy(a, a+4, b);

  // In C++11, you can also use this:
  std::copy(std::begin(a), std::end(a), std::begin(b));

  // use of vectors
  std::vector<int> va(a, a+4); // copies the content of a into the vector
  std::vector<int> vb = va;    // vb is a copy of va

  // this initialization is only valid in C++11:
  std::vector<int> vc { 5, 6, 7, 8 }; // note: no equal sign!

  // assign vc to vb (valid in all standardized versions of C++)
  vb = vc;

  //alternative assignment, works also if both container types are different
  vb.assign(vc.begin(), vc.end());

  std::vector<int> vd; // an *empty* vector

  // you also can use std::copy with vectors
  // Since vd is empty, we need a `back_inserter`, to create new elements:
  std::copy(va.begin(), va.end(), std::back_inserter(vd));

  // copy from array a to vector vd:
  // now vd already contains four elements, so this new copy doesn't need to
  // create elements, we just overwrite the existing ones.
  std::copy(a, a+4, vd.begin());

  // C++11 only: Define a `std::array`:
  std::array<int, 4> sa = { 9, 10, 11, 12 };

  // create a copy:
  std::array<int, 4> sb = sa;

  // assign the array:
  sb = sa;
}
Grace
  • 876
  • 1
  • 11
  • 21
celtschk
  • 19,311
  • 3
  • 39
  • 64
  • why are you writing std all the time instead of just using the namespace of std ??? – Black Jun 30 '15 at 07:04
  • can't you do memcpy(b, a, sizeof a); too? – M4rk Oct 20 '15 at 21:35
  • A Java array is more like `std:array` than like `std::vector`, because it has a fixed size. – Bart van Heukelom Jan 20 '16 at 15:59
  • Does `std::begin()` buy you anything in your second example of `std::copy`? – wcochran Aug 12 '16 at 15:10
  • @wcochran: Yes: Should you ever decide to rewrite the code to use an actual container instead of a built-in array, you will not have to change that line. The less code you need to change, the less bugs you will introduce (and the less work you will have). – celtschk Aug 12 '16 at 16:01
20

Use memcpy in C, std::copy in C++.

user541686
  • 205,094
  • 128
  • 528
  • 886
  • For a small array I assume neither incur any function call overhead (`memcpy` should be a compiler intrinsic)? – wcochran Aug 12 '16 at 15:09
  • @Mehrdad I didn't say otherwise; just making a comment. And I didn't downvote it, either. – MD XF Dec 06 '16 at 23:28
19

You can use the memcpy(),

void * memcpy ( void * destination, const void * source, size_t num );

memcpy() copies the values of num bytes from the location pointed by source directly to the memory block pointed by destination.

If the destination and source overlap, then you can use memmove().

void * memmove ( void * destination, const void * source, size_t num );

memmove() copies the values of num bytes from the location pointed by source to the memory block pointed by destination. Copying takes place as if an intermediate buffer were used, allowing the destination and source to overlap.

Ed S.
  • 122,712
  • 22
  • 185
  • 265
Deepu
  • 7,592
  • 4
  • 25
  • 47
  • 3
    Gonna have to -1 here. The OP is specifically asking for a C++ solution and this answer says nothing of the situations in which `memcpy` is wrong, i.e., copying bytes is insufficient. – Ed S. Apr 22 '13 at 01:18
  • 3
    @EdS. In case you haven't noticed, the OP is now asking for a C *or* C++ solution. – autistic Apr 22 '13 at 02:15
  • 6
    When I answered the OP was asking for C/C++ solutions, though I personally believe "C/C++" is insult to both the languages. :) – Deepu Apr 22 '13 at 02:22
  • fair enough, I didn't realize it was changing. Maybe it even said that earlier and I missed it. -1 removed. – Ed S. Apr 22 '13 at 04:20
  • @EdS. It always said "a function in C or C++". – Jim Balter Apr 22 '13 at 05:33
  • @JimBalter: Like I said: "Maybe it even said that earlier and I missed it". Of course, there is no one answer for two different languages. – Ed S. Apr 22 '13 at 16:59
  • @EdS "Like I said" ... yes, I know that. You speculated that it said it earlier; I asserted that it always said it ... no edit shows differently. – Jim Balter Apr 22 '13 at 19:48
16

I like the answer of Ed S., but this only works for fixed size arrays and not when the arrays are defined as pointers.

So, the C++ solution where the arrays are defined as pointers:

#include <algorithm>
...
const int bufferSize = 10;
char* origArray, newArray;
std::copy(origArray, origArray + bufferSize, newArray);

Note: No need to deduct buffersize with 1:

  1. Copies all elements in the range [first, last) starting from first and proceeding to last - 1

See: https://en.cppreference.com/w/cpp/algorithm/copy

jaques-sam
  • 2,578
  • 1
  • 26
  • 24
12

In C you can use memcpy. In C++ use std::copy from the <algorithm> header.

Pete Becker
  • 74,985
  • 8
  • 76
  • 165
6

I give here 2 ways of coping array, for C and C++ language. memcpy and copy both ar usable on C++ but copy is not usable for C, you have to use memcpy if you are trying to copy array in C.

#include <stdio.h>
#include <iostream>
#include <algorithm> // for using copy (library function)
#include <string.h> // for using memcpy (library function)


int main(){

    int arr[] = {1, 1, 2, 2, 3, 3};
    int brr[100];

    int len = sizeof(arr)/sizeof(*arr); // finding size of arr (array)

    std:: copy(arr, arr+len, brr); // which will work on C++ only (you have to use #include <algorithm>
    memcpy(brr, arr, len*(sizeof(int))); // which will work on both C and C++

    for(int i=0; i<len; i++){ // Printing brr (array).
        std:: cout << brr[i] << " ";
    }

    return 0;
}
Farid Chowdhury
  • 2,766
  • 1
  • 26
  • 21
  • 4
    [`using namespace std;` is a bad practice](https://stackoverflow.com/q/1452721/2176813). Don't ever use it. Instead of cplusplus.com, please use cppreference.com, which includes much better and up-to-date documentation of the standard. The `stdio.h` equivalent in C++ is `cstdio`, use that instead. Additionally, the code is fairly non-idiomatic C++. I think it'd be much clearer if you had showcased separate solutions for C and C++. – tambre Sep 02 '17 at 17:33
6

Just include the standard library in your code.

#include<algorithm>

Array size will be denoted as n

Your old Array

int oldArray[n]={10,20,30,40,50};

Declare New Array in which you have to copy your old array value

int newArray[n];

Use this

copy_n(oldArray,n,newArray);
Ankit Singh
  • 354
  • 3
  • 5
3

in C++11 you may use Copy() that works for std containers

template <typename Container1, typename Container2>
auto Copy(Container1& c1, Container2& c2)
    -> decltype(c2.begin())
{
    auto it1 = std::begin(c1);
    auto it2 = std::begin(c2);

    while (it1 != std::end(c1)) {
        *it2++ = *it1++;
    }
    return it2;
}
MORTAL
  • 383
  • 2
  • 10
  • It would be a better idea to pull the `std::end` out of the loop, for performance reasons (c1 doesn't change or invalidate iterators during the loop,so it's unnecessary to re-calculate the end). – celtschk Sep 05 '16 at 17:43
3

Firstly, because you are switching to C++, vector is recommended to be used instead of traditional array. Besides, to copy an array or vector, std::copy is the best choice for you.

Visit this page to get how to use copy function: http://en.cppreference.com/w/cpp/algorithm/copy

Example:

std::vector<int> source_vector;
source_vector.push_back(1);
source_vector.push_back(2);
source_vector.push_back(3);
std::vector<int> dest_vector(source_vector.size());
std::copy(source_vector.begin(), source_vector.end(), dest_vector.begin());
1

Try this :

  1. Create an empty array.
  2. Insert the elements.
  3. Create a duplicate empty array of the same size.
  4. Start for i=0 to i=array length.
    5. newarray[i]=oldarray[i] (only for C++)

C++ program

#include<iostream>
using namespace std;
int main()
{
        int initA[100],finA[100],i,size;
        cout<<"Input the size of the array : ";
        cin>>size;
        cout<<"Input the elements of the first array";
        for(i=0;i<size;i++)
        {
               cin>>initA[i];
        }
        for(i=0;i<size;i++)
        {
             finA[i]=initA[i];
        }
        cout<<"The final array is\n";
        for(i=0;i<size;i++)
               cout<<finA[i]<<" ";
        return 0;
}
Dada
  • 6,313
  • 7
  • 24
  • 43
0

C++ 20

You can use std::ranges::copy

as simple, as std::ranges::copy(a, b);

#include <algorithm> // ranges::copy, ranges::copy_if
#include <iostream>  // cout
#include <iterator>  // ostream_iterator, begin, end
#include <numeric>   // iota

int main()
{
    float source[10];
    std::iota(std::begin(source), std::end(source), 0);

    float destination[10];

    std::ranges::copy(source, destination);

    std::cout << "destination contains: ";
    std::ranges::copy(destination, std::ostream_iterator<float>(std::cout, " "));
    std::cout << '\n';

    std::cout << "odd numbers in destination are: ";

    std::ranges::copy_if(destination, std::ostream_iterator<float>(std::cout, " "),
                         [](int x) { return (x % 2) == 1; });
    std::cout << '\n';
}

https://coliru.stacked-crooked.com/view?id=1a20680b445b5749

OwnageIsMagic
  • 1,949
  • 1
  • 16
  • 31