2

I have a small program.

I wanted to get the number of elements of the array p1. When I debug, I get 0. But I think it should be 6.

// ConsoleApplication3.cpp : Definiert den Einstiegspunkt für die Konsolenanwendung.
//

#include "stdafx.h"
#include <iostream>
#include <stdio.h>
using namespace std;

double array_concat(double p1[], double p2[])
{
    double ans[2][6];
    int i, j;
    i = 0;
    printf("%d\n", sizeof(p1) / sizeof(p1[0])); //is this wrong?
    for (j = 0; j < sizeof(p1) / sizeof(p1[0]); j++){
        ans[i][j] = p1[j];
    }
    i = 1;
    for (j = 0; j < sizeof(p1) / sizeof(p1[0]); j++){
        ans[i][j] = p2[j];
    }

    return ans[2][6];
}


int _tmain(int argc, _TCHAR* argv[])
{
    cout << "Hello\n";
    int i;
    double c[2][6];
    double p1[6] = { 0, 1, 0, 0, 0, 0 };
    double p2[6] = { 1, 1, 0, 0, 0, 0 };

    c[2][6] = array_concat(p1, p2);

    for (i = 0; i < 12; i++){
        printf("%lf\n", c[i]); //is this wrong?
    }

    return 0;
}

What was wrong?

Edited code, so the p1,p2 and the return value of the function should better be poiters. I made it as in the example https://www.kompf.de/cplus/artikel/funcpar.html, but somehow it doesn't work. // ConsoleApplication3.cpp : Definiert den Einstiegspunkt für die Konsolenanwendung. //

    #include "stdafx.h"
    #include <iostream>
    #include <stdio.h>
    using namespace std;

    double **array_concat(double *p1, double *p2)
    {
    double** ans = 0;
    //ans = new double*[2];
        //double ans[2][6];
        int i, j;
        i = 0;
        printf("%d\n", sizeof(p1) / sizeof(p1[0])); //is this wrong?
        for (j = 0; j < sizeof(p1) / sizeof(p1[0]); j++){
            ans[i][j] = p1[j];
        }
        i = 1;
        for (j = 0; j < sizeof(p1) / sizeof(p1[0]); j++){
            ans[i][j] = p2[j];
        }

        return ans;
    }


    int _tmain(int argc, _TCHAR* argv[])
    {
        cout << "Hello\n";
        int i;
        //double c[2][6];
        double p1[6] = { 0, 1, 0, 0, 0, 0 };
        double p2[6] = { 1, 1, 0, 0, 0, 0 };

        //double *c;
        double **c = array_concat(p1, p2);

        for (i = 0; i < 12; i++){
            printf("%lf\n", c[i]); //is this wrong?
        }

        return 0;
    }
Bobotic
  • 43
  • 1
  • 9

1 Answers1

3

In array_concat() p1 is a pointer, not an array. Arrays are not first-class data types in C and cannot be passed as function arguments; instead they 'decay' to pointers.

The array argument syntax is misleading, and should be avoided in most cases, to avoid confusion.

Clifford
  • 88,407
  • 13
  • 85
  • 165
  • I get where you're coming from but I think it's debateable as to whether arrays are first-class data types, at least in C++. Sure, they're non-copyable. Okay. But in every other way, they match the criteria. They are a formal set of compound types, _just as pointers are_. You can chuck around references to them just fine. Array types exist, strongly. Calling them "not first class data types" is liable to mislead people into thinking some nonsense like "arrays are just syntactic sugar for pointers". And there are plenty of other types that cannot be copied... – Lightness Races in Orbit May 11 '16 at 12:08
  • ... I think the bigger problem is that C's semantics result in a situation where the conventional "first-class data type" definition doesn't perfectly fit anyway. I'd completely avoid it in this context – Lightness Races in Orbit May 11 '16 at 12:09
  • thanks, can you pls look at the edited version – Bobotic May 11 '16 at 12:30
  • @bobotic : The edit does not change the answer other than rendering the advice about syntax and the reference to C nonsense, and making the question less reasonable. What is the sizeof a pointer? It is not the size of the array pointed to. Also if you are using C++ there are better solutions available, than writing C code and compiling it as C++. – Clifford May 12 '16 at 06:32
  • @LightnessRacesinOrbit : I am not going to debate it, but simply specify the source I am using for the term: [here](https://en.wikipedia.org/wiki/First-class_citizen): *"These operations typically include being passed as an argument, returned from a function, and assigned to a variable"* - neither of which are directly possible with an array. What are the "other types that cannot be copied"? Moreover the question was not originally tagged C++ and at a cursory glance it looks a lot like C code. – Clifford May 12 '16 at 10:11
  • @Clifford: There are infinite types that cannot be copied; just delete the copy constructor. `std::unique_ptr` is an obvious example. – Lightness Races in Orbit May 12 '16 at 10:14
  • The tag is certainly correct; from the first revision, the OP's code has been valid C++ and invalid C. Code with `#include ` on it does not "look like C code" to you, me or a compiler! – Lightness Races in Orbit May 12 '16 at 10:15
  • @LightnessRacesinOrbit : Regarding the tagging, you responded while I was modifying my comment. – Clifford May 12 '16 at 10:16
  • @LightnessRacesinOrbit : Certainly a library or user defined class can be rendered non-copyable, I would distinguish these from fundamental built in types - the semantics can be modified in many ways. Deleting the copy constructor is not enough however is it? - a default will be supplied. It must be explicitly declared `private`. Not the place for this discussion however. – Clifford May 12 '16 at 10:21
  • @Clifford: No, in C++, "deleting the copy constructor" (and this is standard terminology) means declaring it with the `delete` keyword, which most certainly is enough. It's true that in the old 1998 version you would have to use the workaround of making it `private` instead. – Lightness Races in Orbit May 12 '16 at 10:22
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/111741/discussion-between-clifford-and-lightness-races-in-orbit). – Clifford May 12 '16 at 10:23