昨天我在第一学期结束时参加了编程I的考试。这是非常基本的,除了我犯了一个非常,非常模糊的错误,我想问这里有经验的人:
我基本上有一个类库,其中包含一个包含Loan *元素的向量,其中包含Customer和Book类。有点像这样:
class Library
{
vector<Loan*> loans_;
};
class Loan
{
Customer *customer_;
Book *book_;
};
我有一个功能,需要浏览所有已初始化的书籍对象并查看哪些属于谁,如下所示:
Customer *getBorrower(Book *book)
{
vector<Loan*>::iterator iter;
for( iter = loans_.begin(); iter != loans_.end(); ++iter )
{
if( (*iter).getBook() == book )
return (*iter).getCustomer();
else
continue;
}
return 0;
}
这让我很难过,因为在Netbeans 6.9 IDE中(* iter)。向我展示了贷款对象的所有方法的列表。
当我加载VC ++ 08时,我正准备退出考试,它问我是否不想使用->
。
(*iter)->getBook();
让我很懊恼。
所以我的问题是:为什么IDE允许我使用.
甚至吐出方法列表以及->
?据我所知,它不会在任何时候发生这种疯狂。这到底发生了什么?我不明白我试图让这个方法做了什么让我觉得奇怪的netbeans错误“不是类型贷款*”
第二个问题:这是一个风格问题。我向教授评论过这个问题,但他似乎并不太满意。考试指南也让我们创建了一个公共
vector<Book*>
和vector<Customer*>
。
然后我们从main函数访问这些来运行我们的单元测试。我发现这是非常糟糕的做法,因为简单的getter函数会为我们提供我们所需要的而不会公开我们的信息。我认为这是一个糟糕的设计选择吗?
错误:
Library.cpp:14:错误:请求成员getCustomer' in
(&amp; iter) - &gt; __ gnu_cxx :: __ normal_iterator&lt; _Iterator,_Container&gt; :: operator * with _Iterator = Loan **,_ Container = std :: vector&gt;',它是非类型的`Loan *'
答案 0 :(得分:2)
表达式(*iter)->getBook()
应该有效。类型vector<T>::iterator
是“指向”T
的实例,通常是普通的T*
。在您的情况下,T
为Loan*
,因此T*
为Loan**
。因此iter
是Loan**
,因此(*iter)
是Loan*
,您可以使用->
运算符进行访问。
很可能NetBeans像你一样困惑,尽管它没有任何借口。 : - )
答案 1 :(得分:2)
好吧,似乎Intellisense比NetBeans更好。 ;)
在这种情况下, (*iter)->getBook()
是获取方法的正确方法。请注意,迭代器是一种带有重载运算符*
和->
的指针,其行为类似于普通指针。
在您的情况下,*iter
是向量中的元素的取消引用,它是指针。因此,如果要访问该方法,则必须使用运算符->
,因此构造(*iter)->getBook()
有效。以及更加模糊的方法:(*(*iter)).getBook()
。
答案 2 :(得分:1)
在C中,(*foo).bar
将遵循指向foo结构的foo
指针并找到bar
成员。因为这是一个繁琐的输入量,所以引入了foo->bar
来跟随指向foo结构的foo
指针并找到bar
成员。
因此,您必须根据您是使用指向结构的指针还是使用结构来选择使用.
vs ->
。
请注意,我不知道C ++如何扩展->
和.
对类的使用,但由于第一个C ++实现基于带结构的C,我假设 ->
和.
以相同的方式处理类:使用class
取消引用类型.
的对象,并取消引用类型为pointer to class
的对象与->
。但这就是我的猜想。