Du bist nicht angemeldet.

Stilllegung des Forums
Das Forum wurde am 05.06.2023 nach über 20 Jahren stillgelegt (weitere Informationen und ein kleiner Rückblick).
Registrierungen, Anmeldungen und Postings sind nicht mehr möglich. Öffentliche Inhalte sind weiterhin zugänglich.
Das Team von spieleprogrammierer.de bedankt sich bei der Community für die vielen schönen Jahre.
Wenn du eine deutschsprachige Spieleentwickler-Community suchst, schau doch mal im Discord und auf ZFX vorbei!

Werbeanzeige

benjs

Frischling

  • »benjs« ist der Autor dieses Themas

Beiträge: 19

Beruf: Schüler

  • Private Nachricht senden

1

15.07.2013, 22:48

[C++] Funktionsüberladung - Problem mit Vector2f und float

Hallo,

heute habe ich wieder Lust gehabt C++ zu lernen, deshalb verzeiht mir bitte wenn die Frage dämlich ist :)
Ich habe angefangen mit der SFML ein kleines Spiel zu programmieren und soweit funktioniert auch alles. Weil die Vektoren von der SFML aber keine Hilfsfunktionen haben, wollte ich mir einen kleinen math-namespace schreiben, bei dem ich aber jetzt hängen geblieben bin, denn anscheinend erkennt der Compiler nicht die Typen der Parameter (VC++)

Folgender Fehler tritt zweimal auf:

Quellcode

1
2
1>c:\users\admin\documents\visual studio 2010\projects\sfml-dev\sfml-dev\math.cpp(8): error C2664: 'math::clamp': Konvertierung des Parameters 1 von 'float' in 'const sf::Vector2f &' nicht möglich
1>          Ursache: Konvertierung von 'float' in 'const sf::Vector2f' nicht möglich


Meine Math.hpp:

C-/C++-Quelltext

1
2
3
4
5
6
7
8
#pragma once
#include <SFML\System.hpp>

namespace math
{
    static sf::Vector2f clamp(const sf::Vector2f& min, const sf::Vector2f& max, const sf::Vector2f& x);
    static float clamp(const float& min, const float& max, const float& x);
}


Und das sind die beiden Funktionen:

C-/C++-Quelltext

1
2
3
4
5
6
7
8
9
10
11
12
13
14
#include <SFML\System.hpp>

namespace math
{
    static inline sf::Vector2f clamp(const sf::Vector2f& min, const sf::Vector2f& max, const sf::Vector2f& x)
    {
        return sf::Vector2f(math::clamp(min.x, max.x, x.x), math::clamp(min.y, max.y, x.y));
    }

    static inline float clamp(const float& min, const float& max, const float& x)
    {
        return (x < min ? min : (x > max ? max : x));
    }
}


In Zeile 7 habe ich auch versucht, die Typen explizit anzugeben, doch der Fehler bleibt der selbe:

C-/C++-Quelltext

1
return sf::Vector2f(math::clamp((float)min.x, (float)max.x, (float)x.x), math::clamp((float)min.y, (float)max.y, (float)x.y));


Man könnte die Funktionen natürlich umbenennen (à la clampVector), aber mich würde es interessieren, wieso das jetzt nicht funktioniert. Gegoogelt habe ich nach dem Fehler natürlich auch schon, doch dort sind die Probleme für mich offensichtlicher und hier sind das auch unterschiedliche Typen... Ich programmiere jetzt schon 3 Jahre mit dem .Net Framework, da ist mir sowas noch nie passiert!

Für allgemeine Tipps bin ich natürlich auch sehr dankbar.
Ich würde mich über Hilfe sehr freuen.

MfG,
benjs

2

15.07.2013, 23:15

Hmmm,
hab das mal kopiert und bei mir funktioniert alles problemlos.
( VisualStudio 2012 )

//EDIT:
Hatte alles in die main.cpp kopiert.
Musst inline und static entfernen, dann gehts. :D

Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von »Maxomann« (15.07.2013, 23:39)


benjs

Frischling

  • »benjs« ist der Autor dieses Themas

Beiträge: 19

Beruf: Schüler

  • Private Nachricht senden

3

15.07.2013, 23:36

Danke, dann muss es wohl an etwas anderem liegen, obwohl ich mir Visual Studio 2010 Express erst gestern heruntergeladen habe und sogut wie nichts eingestellt habe (für Windows 7 32bit). In den Projekteinstellungen habe ich nur ein zusätzliches Include- und Bibliotheksverzeichnis für SFML 2.0 hinzugefügt, für die Debug-Konfiguration die Lib's mit dem Postfix -d.

Ich habe die Funktion auch mal umbenannt, sodass es keine Parameterüberladung mehr gibt, dann treten aber folgende Fehler zweimal auf:

Quellcode

1
2
1>c:\users\admin\documents\visual studio 2010\projects\sfml-dev\sfml-dev\math.cpp(7): error C2039: 'clamp': Ist kein Element von 'math'
1>c:\users\admin\documents\visual studio 2010\projects\sfml-dev\sfml-dev\math.cpp(7): error C3861: "clamp": Bezeichner wurde nicht gefunden.


Das finde ich auch sehr merkwürdig.


Fehler gefunden:
Ein #include "Math.hpp" hat gefehlt. Ich brauche dringend eine Pause :)

MfG
benjs

dot

Supermoderator

Beiträge: 9 757

Wohnort: Graz

  • Private Nachricht senden

4

16.07.2013, 00:31

Kleine Anmerkung am Rande: Das static dort tut nicht, was du denkst, dass es tut und inline ist ziemlich witzlos, wenn du die Definition in eine separate .cpp Datei auslagerst... ;)
Lass das static auf jeden Fall weg und entweder inline und Definition im Header oder Definition in .cpp und nicht inline.

benjs

Frischling

  • »benjs« ist der Autor dieses Themas

Beiträge: 19

Beruf: Schüler

  • Private Nachricht senden

5

17.07.2013, 17:47

Ok, vielen Dank, habe es geändert und es funktioniert auch soweit.
Kann man denn dann auch noch weitere Funktionen im Header deklarieren?

Denn ich habe folgendes hinzugefügt:

Math.hpp

C-/C++-Quelltext

1
2
3
4
5
6
7
8
9
10
11
12
13
14
namespace math
{
    float lengthSquared(const sf::Vector2f& a); // <- Deklaration

    inline sf::Vector2f clamp(const sf::Vector2f& min, const sf::Vector2f& max, const sf::Vector2f& x)
    {
        // [...]
    }

    inline float clamp(const float& min, const float& max, const float& x)
    {
        // [...]
    }
}


Math.cpp

C-/C++-Quelltext

1
2
3
4
5
6
7
8
9
10
#include "Math.hpp"

namespace math
{
    float math::lengthSquared(const sf::Vector2f& a)
    {
        return a.x * a.x + a.y * a.y;
    }

}


... und der Fehler tritt erneut auf. Was mache ich falsch?

Fehler:

Quellcode

1
2
3
1>c:\users\admin\documents\visual studio 2010\projects\sfml-dev\sfml-dev\math.hpp(10): error C2664: 'math::clamp': Konvertierung des Parameters 1 von 'const float' in 'const sf::Vector2f &' nicht möglich
1>          Ursache: Konvertierung von 'const float' in 'const sf::Vector2f' nicht möglich
1>          Quelltyp konnte von keinem Konstruktor angenommen werden, oder die Überladungsauflösung des Konstruktors ist mehrdeutig


Edit:
Habe den Fehler gefunden. Zu dem Zeitpunkt von dem Vector2f clamp() war dem Compiler das float clamp() noch nicht bekannt. Musste also nur die Vector2f clamp() dahinter schreiben, und dann hats funktioniert.

Und noch eine Frage: Was tut das static denn? Ist das sowas wie ein internal in C#, also dass man die Funktion nur Assemblyweit aufrufen kann?

MfG,
benjs

Dieser Beitrag wurde bereits 6 mal editiert, zuletzt von »benjs« (17.07.2013, 18:06)


dot

Supermoderator

Beiträge: 9 757

Wohnort: Graz

  • Private Nachricht senden

6

17.07.2013, 18:48

Ich würde mal vermuten, dass das Problem ist, dass die float Variante nicht vor der Definition der sf::Vector2f Variante deklariert wurde und daher dem Compiler an der Stelle noch nicht bekannt ist...

benjs

Frischling

  • »benjs« ist der Autor dieses Themas

Beiträge: 19

Beruf: Schüler

  • Private Nachricht senden

7

17.07.2013, 19:57

Jup, das war das Problem.

Das static dort tut nicht, was du denkst [...]

Rein interessehalber - was macht das static dort denn? Ich habe mal gegoogelt und gefunden, dass die Funktion dann nur innerhalb einer "translation unit" gilt. Heißt das, dass die nur innerhalb der Datei aufrufbar ist (wie bei C# internal) ?

patrick246

Treue Seele

Beiträge: 328

Wohnort: nahe Heilbronn/BW

Beruf: TG Profil Informatik-Schüler

  • Private Nachricht senden

8

17.07.2013, 21:04

Ja, diese Funktion kann nur innerhalb einer .o-Datei aufgerufen werden.

Werbeanzeige