为啥模板类不能正常工作双重?

Posted

技术标签:

【中文标题】为啥模板类不能正常工作双重?【英文标题】:Why template class not working properly for double?为什么模板类不能正常工作双重? 【发布时间】:2014-10-17 03:30:46 【问题描述】:

我有以下代码:

#include<cstdio>
#include<iostream>
#include<cmath>
using namespace std;
template <class T> class Stack

private:
    T a[1001];
    int i=0,j;
public:
    void pop(void)
    
        a[i-1]=0.0;
        a[i-1]='\0';
    
    void push(T &x)
    
        a[i++]=x;
    
    void push(const char &x)
    
        a[i++]=x;
    
    void top(void)
    
        cout<<a[i-1];
    
;
int main()

    Stack<char>s1;
    s1.push('a');
    s1.push('b');
    s1.top();
    s1.pop();
    cout<<"\n";

    Stack<int>s2;
    s2.push(10);
    s2.push(20);
    s2.top();
    s2.pop();
    cout<<"\n";

    Stack<double>s3;
    s3.push(5.50);
    s3.push(7.50);
    s3.top();
    s3.pop();
    cout<<"\n";

    return 0;

输出:

b
20
7

为什么双倍显示 7 而不是 7.5? 当我明确专门针对 double 并且不使用引用运算符时,它运行良好。

void push(double x)

    a[i++]=x;

这为双精度提供了正确的输出。 但是,当我这样做时,它会出错。

void push(T x)

    a[i++]=x;

void push(const char &x)

    a[i++]=x;

如何解决这个问题? 如何显示双精度输出?

【问题讨论】:

左值引用不能绑定到右值。 另外,你没有“专门化”任何东西。 OT,但你的 pop 函数实际上并没有递减 i @MattMcNabb 我知道,它不会减少 i。我只是用它来显示输出。 【参考方案1】:

当你使用

s3.push(7.50);

它解决了重载

void push(const char &x)

    a[i++]=x;

由于7.5无法转换为double&amp;,需要使用:

void push(T &x)

    a[i++]=x;

因此,您会在堆栈中获得7 的截断值。

如果您希望调用解析为void push(T &amp;x),请创建一个变量并在调用中使用该变量。

double x = 7.5;
s3.push(x);

【讨论】:

@KhairulBasar 当参数类型为const&amp;时,输入值在临时内存位置被截断,并将临时内存位置传递给函数。 另一个可能的解决方法是让push 通过值或常量引用获取x 谢谢。但如果我简单地使用 void push(char &x) 它对所有人都很好......可以吗?还是会产生错误?【参考方案2】:

我想补充一下 R Sahu 的回答。在 C++11 中,引入了一种称为 r-value reference 的新型引用。 R 值引用用于引用未命名变量,在本例中就是 7.5。

R Sahu 所说的“7.5 无法转换为 double&amp;”的意思是 l 值引用,即您的 double&amp;不能绑定到r-value,即你的7.5

左值引用T&amp; 只能绑定到左值。 R 值引用T&amp;&amp; 只能绑定到 r 值。 只读 l-value 引用const T&amp; 但是,可以绑定到 l-value 或 r-value,只读或非只读。因此,函数重载解析将解析为push(const char&amp; x),因为它采用只读左值引用

感谢您的阅读。

【讨论】:

以上是关于为啥模板类不能正常工作双重?的主要内容,如果未能解决你的问题,请参考以下文章

为啥我不能返回对使用模板创建的派生类的 unique_ptr 的引用?

为啥 g++ 需要模板类及其友元函数的定义?

为啥 GL_RASTERIZER_DISCARD 不能让我写入模板缓冲区?

为啥我不能从 gcc 中的前身模板化成员函数访问祖先方法?

c++创建链表为啥要用类模板

为啥未使用的成员模板函数的类模板实例化失败