c++ friend 遇到 namespace 无法访问 private 成员的问题

相关的文章(比较有意思,记录一下):http://www.cnblogs.com/lx20030303/archive/2012/09/21/2696258.html

先看例子。如下。

尝试编译的话,错误提示:

Entrance.cpp
src\Entrance.cpp(15) : error C2248: “lqr::Entrance::id”: 无法访问 private 成员
(在“lqr::Entrance”类中声明)
C:\Users\Administrator\Desktop\tmp\include\Entrance.h(11) : 参见“lqr::E
ntrance::id”的声明
C:\Users\Administrator\Desktop\tmp\include\Entrance.h(9) : 参见“lqr::En
trance”的声明
src\Entrance.cpp(15) : error C2248: “lqr::Entrance::number”: 无法访问 private
成员(在“lqr::Entrance”类中声明)
C:\Users\Administrator\Desktop\tmp\include\Entrance.h(10) : 参见“lqr::E
ntrance::number”的声明
C:\Users\Administrator\Desktop\tmp\include\Entrance.h(9) : 参见“lqr::En
trance”的声明
NMAKE : fatal error U1077: “"D:\Program Files (x86)\Microsoft Visual Studio 12.
0\VC\BIN\cl.EXE"”: 返回代码“0x2”
Stop.

解决办法:把Entrance.cpp的第13行改为ostream& lqr::operator<<(ostream& os, const Entrance& e)

Entrance.h

 1 #ifndef ENTRANCE_H
 2 #define ENTRANCE_H
 3
 4 #include <iostream>
 5
 6 namespace lqr {
 7
 8     class Entrance
 9     {
10         unsigned int number;
11         int id;
12     public:
13         Entrance(unsigned int number, int id);
14         friend std::ostream& operator<<(std::ostream& os, const Entrance& e);
15     };
16
17 }
18
19 #endif // ENTRANCE_H

Entrance.cpp

 1 #include "Entrance.h"
 2 #include <iostream>
 3
 4 using namespace lqr;
 5 using namespace std;
 6
 7 Entrance::Entrance(unsigned int number_val, int id_val)
 8     :number(number_val), id(id_val)
 9 {
10     // do nothing
11 }
12
13 ostream& operator<<(ostream& os, const Entrance& e)
14 {
15     return os << "Entrance #"<< e.id << ": "<< e.number;
16 }

main.cpp

#include "Entrance.h"

#include <iostream>

using namespace std;
using namespace lqr;

int main()
{
    Entrance en(99, 123);

    cout << en << endl;

    return 0;
}

Makefile

# compiler
CC = cl
# linker
LINK = link
# libraries

# headers
HEADER_PATH = /I include
# options
EHSC = /EHsc
COMPILATION_ONLY = /c
C_OUT = /Fo:
L_OUT = /OUT:
# compiler & linker debug option, to disable debug, replace ‘/Zi‘ & ‘/DEBUG‘ with empty strings
C_DEBUG = /Zi
L_DEBUG = /DEBUG
# C_DEBUG =
# L_DEBUG =
# targets
bin\test.exe: bin obj obj\main.obj obj\Entrance.obj
    $(LINK) $(L_DEBUG) $(L_OUT)bin\test.exe obj\main.obj obj\Entrance.obj

obj\main.obj: src\main.cpp include\Entrance.h
    $(CC) $(C_DEBUG) $(EHSC) $(HEADER_PATH) $(COMPILATION_ONLY) src\main.cpp $(C_OUT)obj\main.obj

obj\Entrance.obj: src\Entrance.cpp include\Entrance.h
    $(CC) $(C_DEBUG) $(EHSC) $(HEADER_PATH) $(COMPILATION_ONLY) src\Entrance.cpp $(C_OUT)obj\Entrance.obj

# folders

obj:
    mkdir obj

bin:
    mkdir bin

# clean
# bin, obj folders and pdb files

.PHONY: clean
clean:
    -rmdir /s /q bin
    -rmdir /s /q obj
    -del *.pdb
时间: 2024-08-04 23:49:16

c++ friend 遇到 namespace 无法访问 private 成员的问题的相关文章

“CObject::operator =”: 无法访问 private 成员(在“CObject”类中声明)

c++工程编译报错: “CObject::operator =”: 无法访问 private 成员(在“CObject”类中声明) 错误无法直接定位源码位置,网上搜索了,也和我的代码不一样. 最后还是自己认真检查代码,发现了个问题 头文件定义了一个CEvent x, 源码文件中使用了 x = new CEvent(true,false); 原来是这里错误了,x是一个直接实例化了的对象,不能再指向另一个实例,只有指针才能这样用. 于是改为CEVent* x;就可以了.

error C2248: “CObject::operator =”: 无法访问 private 成员(在“CObject”类中声明)

MFC编码时报错: 显示:error C2248: "CObject::operator =": 无法访问 private 成员(在"CObject"类中声明) 这种问题是你刚开始声明的是指针类型变量,后来又改为了非指针型,最好直接使用指针型变量. 

C++用指针访问private 成员

// //  main.cpp //  使用指针访问类中的私有变量 // //  Created by 就不告诉你我是谁 on 15-7-25. //  Copyright (c) 2015年 xuqigang. All rights reserved. // #include <iostream> using namespace std; class Class1{ public: Class1(){ } private: int a=10; int k=100; }; int main(i

VC++ error C2248: &ldquo;CObject::CObject&rdquo;: 无法访问 private 成员(在&ldquo;CObject&rdquo;类中声明)

在使用诸如:CArray或是 CList等类时,经常会出现此错误 此错误的原因是由于自定义的类的数组项时 有一个操作如  Add()  在这个操作中,实际上需要一个 = 操作,但是这个 =操作在 自定义类中没有实现,于是,程序自动去它的parent 类 也就是 CObject 类去找,但是却找到个这个类的 = 是一个 private  于是就报了这个错误. 知道了原因解决方法自然就有了,那就是在自定义类中 重载操作符 =   重载后 这个错误就没有了. class COptRect : publ

反射——反射访问私有成员

//BindingFlags.NonPublic | BindingFlags.Instance标志枚举,用于访问私有成员 namespace 通过反射访问私有成员 { class Program { static void Main(string[] args) { Type getMoth = typeof(person); MethodInfo info = getMoth.GetMethod("SayHi",BindingFlags.NonPublic | BindingFla

空指针访问类成员函数

//空指针访问类成员函数 1 #include<iostream> 2 #include<string> 3 using namespace std; 4 5 class Person 6 { 7 public: 8 void showinfo() 9 { 10 cout << "空指针访问成员函数成功" << endl; 11 } 12 13 void showinfo1() 14 { 15 cout << age <

数据持久化、单例、重载【添加对不可访问的成员的操作】、魔术方法、类常量、static关键字对self的补充【静态延迟绑定实现$this的效果】、参数类型约束【参数前加类名】、遍历【iterator接口】、快速排序

1.数据持久化过程[传输(例如表单提交或php交互mysql)和保存过程] 使用的是字符串形式的流数据. 数据流就是为了传输[按照序列的形式进行传输] [http://baike.baidu.com/link?url=0MtUQMhFzc_EwJc09rXZV8KlfOL4jis6XNbRfmGA3rQhDcGwOp8togLVQjXBV34M] 所以将其他类型数据转化为字符串的过程也是序列化的过程 [这个概念和图片.视频的流媒体的区别?] [注意点] 另外mysql中sql语句中的某些关键词为

Java如何访问private变量

大家都知道private变量是无法访问的,一编译就报错根本无法访问啊.本文教你如何破解这种限制. 实现的原理是利用了Java的反射机制. 首先定义一个最简单的类,只有一个私有变量和一个公开的方法.代码如下: class Foo { private String message = "This is a Foo."; public void show() { System.out.println(message); } } 正常情况下调用show函数会输出“This is a Foo.”

Java中的null对象也可以访问static成员变量和方法

声明:本博客为原创博客,未经允许,不得转载!小伙伴们如果是在别的地方看到的话,建议还是来csdn上看吧(链接为 http://blog.csdn.net/bettarwang/article/details/26515271),看代码和提问.讨论都更方便. 一般来说,一个类的对象要在实例化之后才可以访问类中的成员变量和方法.如果它还是null,通常意义上我们就认为它不能访问类中的成员.实际上确实不提倡这样,而且null对象确实不能访问实例成员(变量和方法),否则会引发NULLPointerExc