Jump to content

  • Log In with Google      Sign In   
  • Create Account

14 years ago on June 15th Gamedev.net was first launched! We want to thank all of you for being part of our community and hope the best years are ahead of us. Happy birthday Gamedev.net!

[C++, Variable Argument List] Va_Arg() Does Not Retrieve Correct Value


Old topic!
Guest, the last post of this topic is over 60 days old and at this point you may not reply in this topic. If you wish to continue this conversation start a new topic.

  • You cannot reply to this topic
4 replies to this topic

#1 hkBattousai   Members   -  Reputation: 142

Like
0Likes
Like

Posted 10 January 2011 - 04:17 PM

I have this constructor of the template class PolynomialFraction:
template <class T>
PolynomialFraction<T>::PolynomialFraction(uint64_t unNumNomCoef, uint64_t unNumDenCoef, T FirstCoefficient, ... )
{
	std::vector<T> NominatorCoefficients;
	std::vector<T> DenominatorCoefficients;
	va_list ArgumentPointer;
	va_start(ArgumentPointer, FirstCoefficient);
	T NextCoefficient = FirstCoefficient;
	if (unNumNomCoef == 0) // Every polynomial must have at least one coefficient
	{
		NominatorCoefficients.push_back(static_cast<T>(0));
	}
	else
	{
		NominatorCoefficients.push_back(NextCoefficient);
		for (uint64_t i=1; i<unNumNomCoef; i++)
		{
			NextCoefficient = va_arg(ArgumentPointer, T);
			NominatorCoefficients.push_back(NextCoefficient);
		}
	}
	if (unNumNomCoef == 0)
	{
		DenominatorCoefficients.push_back(static_cast<T>(1));
	}
	else
	{
		for (uint64_t i=0; i<unNumDenCoef; i++)
		{
			NextCoefficient = va_arg(ArgumentPointer, T);
			DenominatorCoefficients.push_back(NextCoefficient);
		}
	}
	m_NominatorPolynomial = Polynomial<long double>(NominatorCoefficients);
	m_DenominatorPolynomial = Polynomial<long double>(DenominatorCoefficients);
}

As its name suggests, this class is supposed to hold nominator and denominator polynomials of a polynomial fraction.

Constructor parameters are:
First: Number of coefficients in nominator
Second: Number of coefficients in denominator
Third: First coefficient
The rest: The other coefficients if any.

I'm calling this constructor like below:
PolynomialFraction<long double> pf1(2, 3, 1, 2, 1, 2, 3);
std::cout << pf1.ToString() << std::endl;

Its output is:

(-9.25596e+061x + 1)/(-9.25596e+061x^2 - 9.25596e+061x - 9.25596e+061)

(It is not a bug in ToString() method, I checked it.)

But it should have been:

(2x + 1)/(3x^2 + 2x + 1)


In other words, I don't receive any coefficient except for the very first one.

However, the code below which is a very similar one is working flawlessly:
template <class T>
Polynomial<T>::Polynomial(uint64_t NumberOfCoefficients, T FirstCoefficient, ...)
{
	if (NumberOfCoefficients == 0)
	{
		m_Coefficients.push_back(static_cast<T>(0));
		return;
	}
	va_list ArgumentPointer;
	va_start(ArgumentPointer, FirstCoefficient);
	T NextCoefficient = FirstCoefficient;
	std::vector<T> Coefficients;
	Coefficients.push_back(NextCoefficient);
	for (uint64_t i=1; i<NumberOfCoefficients; i++)
	{
		NextCoefficient = va_arg(ArgumentPointer, T);
		Coefficients.push_back(NextCoefficient);
	}
	m_Coefficients = Coefficients;
}

What am I doing wrong in my code?


Sponsor:

#2 Josh Petrie   Moderators   -  Reputation: 2309

Like
3Likes
Like

Posted 10 January 2011 - 04:27 PM

Your parameters are integers, not doubles. The compiler cannot tell that the arguments passed via the ellipsis should undergo conversion; try passing them explicitly as double literals (that is, 1.0, 2.0, 3.0, et cetera).

Josh Petrie | Lead Tools Engineer, ArenaNet | Microsoft C++ MVP


#3 Martins Mozeiko   Members   -  Reputation: 1179

Like
1Likes
Like

Posted 10 January 2011 - 04:28 PM

You are passing integers to PolynomialFraction constructor (2, 3, 1, ...), but you are expecting long double (second T argument to va_arg macro). That won't work. Pass the correct type.

#4 hkBattousai   Members   -  Reputation: 142

Like
0Likes
Like

Posted 10 January 2011 - 04:36 PM

Ohh guys, thank you.
It is working now. :)


#5 Washu   Senior Moderators   -  Reputation: 3117

Like
0Likes
Like

Posted 10 January 2011 - 05:06 PM

and the reason you're not just simply passing in an array, or an std::vector<double> directly? Instead of playing around with the type-unsafe and quite undefined behavior prone ellipses operator?

In time the project grows, the ignorance of its devs it shows, with many a convoluted function, it plunges into deep compunction, the price of failure is high, Washu's mirth is nigh.
ScapeCode - Blog | SlimDX





Old topic!
Guest, the last post of this topic is over 60 days old and at this point you may not reply in this topic. If you wish to continue this conversation start a new topic.



PARTNERS