Array - Anzahl Elemente



  • Dravere, ich vermute du weisst schon genau was ich meine. Hier mit Code um sich zu werfen bringt wohl nicht mehr viel.
    Wenn ich sage "das Array wird übergeben", meine ich in diesem Fall es wird by-value übergeben, und genau das geht in C++ nicht, da sind wir uns ja denke ich einig.



  • Dravere schrieb:

    Erklär mal an dem Code hier, was passiert. Vor allem würde mich interessieren, wie eine Referenz plötzlich 40 Bytes gross sein kann.

    #include <algorithm>
    
    template<typename T, std::size_t SIZE>
    void foo(T (&ref)[SIZE])
    {
    	std::cout << sizeof(ref) << std::endl;
    	ref[5] = 5;
    }
    
    int main() 
    {
    	int arr[10];
    	std::fill_n(&arr[0], 10, 0);
    
    	int (&ref)[10] = arr;
    
    	std::cout << sizeof(ref) << std::endl;
    
    	foo(arr);
    
    	ref[3] = 3;
    
    	for(int i = 0; i < 10; ++i)
    	{ std::cout << arr[i] << ", "; }
    
    	return 0; 
    }
    

    Ausgabe:

    40
    40
    0, 0, 0, 3, 0, 5, 0, 0, 0, 0,
    

    Grüssli

    das ist leicht damit erklärt, daß die sizeof-funktion nicjt die größe der referenz, sondern die größe des dinges, wo die referenz hinzeigt, anzeigt.

    wenn dur die größe der referenz wirklich anschauen willst, mußt du das so machen:

    template<typename T, std::size_t SIZE>
    void foo(T (&ref)[SIZE])
    {
    	struct Test
    	{
    		T (&ref)[SIZE];
    	};
    	std::cout << sizeof(Test) << std::endl;
    }
    

    ausgabe: 4
    also hat die referenz 4 bytes.



  • call-by-value

    template<class T, unsigned size>
    struct value_array
    {
        T t[size];
    };
    template<class T, unsigned size>
    void func(<value_array<T, size> arr)
    {
        // arr ist eine kopie!
    }
    int main()
    {
        value_array<int, 50> arr;
        func(arr); // kopie!
    }
    

    :p :p



  • helferlein schrieb:

    call-by-value

    template<class T, unsigned size>
    struct value_array
    {
        T t[size];
    };
    template<class T, unsigned size>
    void func(<value_array<T, size> arr)
    {
        // arr ist eine kopie!
    }
    int main()
    {
        value_array<int, 50> arr;
        func(arr); // kopie!
    }
    

    :p :p

    ein nicht-array einfach array zu nennen und damit was über arrays zu beweisen, das geht sogar noch einfacher.

    void f(int arr)//call by value
    {
    }
    int main()
    {
       int array;
       f(array);
    }
    

  • Administrator

    @hustbaer,
    Der erste Post war nicht so ernst gemeint. Der zweite Post war immer noch eher witzig gemeint. Da war ich ja mehr oder weniger immer mit dir einverstanden. Aber was du dann geschrieben hast. Naja, ich muss mich ja nicht nochmals wiederholen 😉
    Man kann nunmal etwas auf zwei Arten übergeben. Dass du zu Beginn pass-by-value meintest, ist für die meisten sicher klar. Deshalb war auch das Smilie da 😉

    @volkard,
    Der Sinn des Codes war aber zu zeigen, dass man keinen Zeiger hat, sondern eben das übergebene Array.
    Der sizeof Operator gibt natürlich bei einer Referenz die grösse des Objektes zurück, auf welche die Referenz referenziert. Laut Standard hat die Referenz keinen adressierbaren Speicher und die grösse ist nicht definiert. Dadurch ist nicht mal sicher, dass das ref in der Struktur Test gleich gross ist, wie das ref, welches im Funktionskopf deklariert wurde. Das hat ja auch den Zweck, dass die Referenz komplett wegoptimiert werden kann, wodurch man direkt mit dem Objekt arbeitet. Es wurde eben das Objekt übergeben.
    Aber ich nehm mal an, dass du das selber weisst 😉

    Grüssli



  • Dravere schrieb:

    @volkard,
    Der Sinn des Codes war aber zu zeigen, dass man keinen Zeiger hat, sondern eben das übergebene Array.
    Der sizeof Operator gibt natürlich bei einer Referenz die grösse des Objektes zurück, auf welche die Referenz referenziert. Laut Standard hat die Referenz keinen adressierbaren Speicher und die grösse ist nicht definiert. Dadurch ist nicht mal sicher, dass das ref in der Struktur Test gleich gross ist, wie das ref, welches im Funktionskopf deklariert wurde. Das hat ja auch den Zweck, dass die Referenz komplett wegoptimiert werden kann, wodurch man direkt mit dem Objekt arbeitet. Es wurde eben das Objekt übergeben.
    Aber ich nehm mal an, dass du das selber weisst 😉

    ja, aber du hast es sehr schön zusammengefaßt.
    weil nicht definiert ist, daß die referenz zum beispiel innendrin nur ein zeiger ist (wie zufällig bei allen mir bekannten implementierungen), sondern weil die compilerbauer da größte freiheiten haben, kann man echt nicht widersprechen, wenn du sagst, daß nicht eine referenz auf ein array übergeben wurde, sondern daß das array per referenz übergeben wurde.
    zu sagen "man kann arrays nicht übergeben" ist nicht haltbar, fürchte ich.



  • volkard schrieb:

    zu sagen "man kann arrays nicht übergeben" ist nicht haltbar, fürchte ich.

    Hmm. Ja. Vielleicht eher das hier:
    Man kann arrays nicht by value übergeben im herkömmlichen Sinne. Respektive es wird keine völlig neue, unabhängige Entität per Kopie erzeugt.



  • drakon schrieb:

    volkard schrieb:

    zu sagen "man kann arrays nicht übergeben" ist nicht haltbar, fürchte ich.

    Hmm. Ja. Vielleicht eher das hier:
    Man kann arrays nicht by value übergeben im herkömmlichen Sinne. Respektive es wird keine völlig neue, unabhängige Entität per Kopie erzeugt.

    Womit wir bei einer genaueren ("korrekteren"), aber für Anfänger vermutlich total unverständlichen Formulierung wären 😉



  • hustbaer schrieb:

    drakon schrieb:

    volkard schrieb:

    zu sagen "man kann arrays nicht übergeben" ist nicht haltbar, fürchte ich.

    Hmm. Ja. Vielleicht eher das hier:
    Man kann arrays nicht by value übergeben im herkömmlichen Sinne. Respektive es wird keine völlig neue, unabhängige Entität per Kopie erzeugt.

    Womit wir bei einer genaueren ("korrekteren"), aber für Anfänger vermutlich total unverständlichen Formulierung wären 😉

    MIST!
    ja, deine formulierung war so hübsch und anfängerfortbringend, daß ich mir überlegt hatte, sie in meine sig aufzunehmen. die welt ist gemein.



  • Also um Anfänger ging es ja seit dem 3. Post nicht mehr. 🙄


Anmelden zum Antworten