| 网站首页 | 业界新闻 | 小组 | 威客 | 人才 | 下载频道 | 博客 | 代码贴 | 在线编程 | 编程论坛
欢迎加入我们,一同切磋技术
用户名:   
 
密 码:  
共有 905 人关注过本帖
标题:大家帮我看看这个程序呀。我调了半天了,还是链接出错。到底哪里错了???
只看楼主 加入收藏
songhuirong1
Rank: 2
等 级:论坛游民
帖 子:116
专家分:38
注 册:2010-6-15
结帖率:94.12%
收藏
已结贴  问题点数:20 回复次数:10 
大家帮我看看这个程序呀。我调了半天了,还是链接出错。到底哪里错了???
这是头文件:
#ifndef QUEUE_H
#define QUEUE_H

#include <iostream>
using namespace std;

template <typename Type>
class QueueItem;

template <typename Type>
class Queue
{
    friend ostream &operator <<(ostream &, const Queue<Type> &);
public:
    Queue();
    ~Queue();

    Type remove();
    void add(const Type &);

    bool is_empty() const;
private:
    QueueItem<Type> *front;
    QueueItem<Type> *back;
};

template <typename Type>
inline Queue<Type>::Queue()
:front(0),back(0)
{}

template <typename Type>
inline Queue<Type>::~Queue()
{
    while(!is_empty())
        remove();
}

template <typename Type>
inline bool Queue<Type>::is_empty() const
{
    return front == 0;
}

template <typename Type>
inline void Queue<Type>::add(const Type &val)
{
    QueueItem<Type> *pt = new QueueItem<Type>(val);

    if(is_empty())
        front = back = pt;
    else
    {
        back->next = pt;
        back = pt;
    }

    back->next = 0;
}

template <typename Type>
inline Type Queue<Type>::remove()
{
    if(is_empty())
    {
        cerr << "remove() on empty queue!" << endl;
        exit(-1);
    }

    QueueItem<Type> *pt = front;
    front = front->next;
    Type resval = pt->item;
    delete pt;

    return resval;
}

template <typename Type>
class QueueItem
{
    friend class Queue<Type>;
    friend ostream &operator <<(ostream &, const QueueItem<Type> &);
public:
    QueueItem(const Type &ie):item(ie) {}
private:
    Type item;
    QueueItem *next;
};

#endif


这是主函数:

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

template <typename Type>
ostream &operator <<(ostream &os, const QueueItem<Type> &q)
{
    os << q.item;

    return os;
}

template <typename Type>
ostream &operator <<(ostream &os, const Queue<Type> &q)
{
    os << "<";

    QueueItem<Type> *p;

    for(p=q.front;p;p=p->next)
        os << *p << " ";
    os << ">";

    return os;
}

int main()
{
    /*Queue<int> *p_qi = new Queue<int>;
    int ival;

    for(ival = 0;ival < 10;++ival)
        p_qi->add(ival);

    int errcnt = 0;

    for(ival = 0;ival < 10;++ival)
    {
        int qval = p_qi->remove();

        if(ival != qval)
            ++errcnt;
    }

    if ( !errcnt )
        cout << "!! queue executed ok\n";
    else
        cerr << "?? queue errors: " << errcnt << endl;*/

    Queue<int> qi;
    cout << qi << endl;

    int ival;

    for(ival=0;ival<10;++ival)
        qi.add(ival);

    //cout << qi << endl;

    return 0;
}

错误显示为:
错误    1    error LNK2019: 无法解析的外部符号 "class std::basic_ostream<char,struct std::char_traits<char> > & __cdecl operator<<(class std::basic_ostream<char,struct std::char_traits<char> > &,class Queue<int> const &)" (??6@YAAAV?$basic_ostream@DU?$char_traits@D@std@@@std@@AAV01@ABV?$Queue@H@@@Z),该符号在函数 _main 中被引用    Queue.obj    CP16
错误    2    fatal error LNK1120: 1 个无法解析的外部命令    F:\Program Files\source\CP16\Debug\CP16.exe    CP16
搜索更多相关主题的帖子: friend 
2011-01-17 11:08
八画小子
Rank: 11Rank: 11Rank: 11Rank: 11
等 级:贵宾
威 望:37
帖 子:709
专家分:2063
注 册:2010-11-11
收藏
得分:1 
大概看了一下,代码中有一些部分被注释了,还存在重复声明变量的情况,应该还有其他问题吧。
2011-01-17 20:12
songhuirong1
Rank: 2
等 级:论坛游民
帖 子:116
专家分:38
注 册:2010-6-15
收藏
得分:0 
回复 2楼 八画小子
就这一个错误,编译是没有问题的,就是链接出错。这个没有重复声明吧,这两个都是友元函数的定义。2楼的去调试一下呀,不要就大概看了一下,看是看不出来的。呵呵。辛苦2楼的了。
2011-01-18 09:01
lintaoyn
Rank: 11Rank: 11Rank: 11Rank: 11
等 级:小飞侠
威 望:4
帖 子:606
专家分:2499
注 册:2009-4-8
收藏
得分:7 
friend ostream &operator << <Type>(ostream &, const Queue<Type> &);
friend ostream &operator << <Type>(ostream &, const QueueItem<Type> &);
QueueItem *next;的访问级别改成public
在VC2008里通过编译

迭代的是人,递归的是神。
2011-01-18 11:20
rjsp
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:528
帖 子:9007
专家分:53942
注 册:2011-1-18
收藏
得分:10 
楼上讲得很好,但按照C++标准,operator <<也需要前置申明,而之所以VC不需要,那是因为VC对模板使用了有问题的“后编译”
template<typename Type> class QueueItem;
template<typename Type> std::ostream& operator<< (std::ostream& os, const QueueItem<Type>& q);
template<typename Type> class Queue;
template<typename Type> std::ostream& operator<< (std::ostream& os, const Queue<Type>& q);

“QueueItem *next;的访问级别改成public”那就不必了,在class QueueItem中加个friend就是
friend std::ostream& operator<< <Type> (std::ostream& os, const Queue<Type>& q);


[ 本帖最后由 rjsp 于 2011-1-19 08:23 编辑 ]
2011-01-18 12:13
八画小子
Rank: 11Rank: 11Rank: 11Rank: 11
等 级:贵宾
威 望:37
帖 子:709
专家分:2063
注 册:2010-11-11
收藏
得分:0 
回复 3楼 songhuirong1
重复声明的是 ival,仔细看一下吧,在同一个域中重复了。
2011-01-18 18:54
songhuirong1
Rank: 2
等 级:论坛游民
帖 子:116
专家分:38
注 册:2010-6-15
收藏
得分:0 
回复 6楼 八画小子
哦。不好意思。本来的第二个ival我是注释掉的,后来忘记了又打开了,这是我的疏忽。但是你没看到问题的本质。呵呵。
2011-01-19 09:09
songhuirong1
Rank: 2
等 级:论坛游民
帖 子:116
专家分:38
注 册:2010-6-15
收藏
得分:0 
回复 4楼 lintaoyn
我按照你的方法去改,结果说显示以下错误:
错误    1    error C2768: “operator <<”: 非法使用显式模板参数    f:\program files\source\cp16\cp16\queue.cpp    11    CP16
错误    2    error C2768: “operator <<”: 非法使用显式模板参数    f:\program files\source\cp16\cp16\queue.cpp    25    CP16
2011-01-19 11:57
songhuirong1
Rank: 2
等 级:论坛游民
帖 子:116
专家分:38
注 册:2010-6-15
收藏
得分:0 
回复 5楼 rjsp
按照你的方法去试,结果成功了。哈哈。太感谢了。
2011-01-19 13:07
songhuirong1
Rank: 2
等 级:论坛游民
帖 子:116
专家分:38
注 册:2010-6-15
收藏
得分:0 
最后程序代码变成了这样:
头文件
程序代码:
#ifndef QUEUE_H
#define QUEUE_H

#include <iostream>
using namespace std;

template <typename Type>
class QueueItem;

template <typename Type>
class Queue
{
    friend ostream &operator << <Type>(ostream &, const Queue<Type> &);
public:
    Queue();
    ~Queue();

    Type remove();
    void add(const Type &);

    bool is_empty() const;
private:
    QueueItem<Type> *front;
    QueueItem<Type> *back;
};

template <typename Type>
inline Queue<Type>::Queue()
:front(0),back(0)
{}

template <typename Type>
inline Queue<Type>::~Queue()
{
    while(!is_empty())
        remove();
}

template <typename Type>
inline bool Queue<Type>::is_empty() const
{
    return front == 0;
}

template <typename Type>
inline void Queue<Type>::add(const Type &val)
{
    QueueItem<Type> *pt = new QueueItem<Type>(val);

    if(is_empty())
        front = back = pt;
    else
    {
        back->next = pt;
        back = pt;
    }

    back->next = 0;
}

template <typename Type>
inline Type Queue<Type>::remove()
{
    if(is_empty())
    {
        cerr << "remove() on empty queue!" << endl;
        exit(-1);
    }

    QueueItem<Type> *pt = front;
    front = front->next;
    Type resval = pt->item;
    delete pt;

    return resval;
}

template <typename Type>
class QueueItem
{
    friend class Queue<Type>;
    friend ostream &operator << <Type>(ostream &, const Queue<Type> &);
    friend ostream &operator << <Type>(ostream &, const QueueItem<Type> &);
public:
    QueueItem(const Type &ie):item(ie) {}
private:
    Type item;
    QueueItem *next;
};

#endif
主函数
程序代码:
#include "Queue.h"
#include <iostream>
using namespace std;

template <typename Type> class QueueItem;

template <typename Type>
ostream &operator <<(ostream &os, const QueueItem<Type> &q)
{
    os << q.item;

    return os;
}

template <typename Type> class Queue;

template <typename Type>
ostream &operator <<(ostream &os, const Queue<Type> &q)
{
    os << "<";

    QueueItem<Type> *p;

    for(p=q.front;p;p=p->next)
        os << *p << " ";
    os << ">";

    return os;
}

int main()
{
    /*Queue<int> *p_qi = new Queue<int>;
    int ival;

    for(ival = 0;ival < 10;++ival)
        p_qi->add(ival);

    int errcnt = 0;

    for(ival = 0;ival < 10;++ival)
    {
        int qval = p_qi->remove();

        if(ival != qval)
            ++errcnt;
    }

    if ( !errcnt )
        cout << "!! queue executed ok\n";
    else
        cerr << "?? queue errors: " << errcnt << endl;*/

    Queue<int> qi;
    cout << qi << endl;

    int ival;

    for(ival=0;ival<10;++ival)
        qi.add(ival);

    cout << qi << endl;

    return 0;
}

这样编译和链接都没问题了,程序正确运行了。看来vs没有完全按照标准C++去设计呀。


[ 本帖最后由 songhuirong1 于 2011-1-19 13:19 编辑 ]
2011-01-19 13:16
快速回复:大家帮我看看这个程序呀。我调了半天了,还是链接出错。到底哪里错了? ...
数据加载中...
 
   



关于我们 | 广告合作 | 编程中国 | 清除Cookies | TOP | 手机版

编程中国 版权所有,并保留所有权利。
Powered by Discuz, Processed in 0.014081 second(s), 7 queries.
Copyright©2004-2024, BCCN.NET, All Rights Reserved