13

为我认为非常基本的问题道歉。

我无法在线找出运算符 :: 和 . 在 C++ 中

我有几年的 C# 和 Java 经验,熟悉使用 . 成员访问的运算符。

谁能解释一下何时使用这些以及有什么区别?

谢谢你的时间

4

7 回答 7

23

区别在于第一个是范围解析运算符,第二个是成员访问语法。

因此,::(范围解析)可用于访问命名空间中的其他内容,如嵌套类,或访问静态函数。句点运算符将简单地访问您正在使用它的类实例的.任何可见成员。

一些例子:

class A {
    public:

        class B { };

        static void foo() {}
        void bar() {}
};

//Create instance of nested class B.
A::B myB; 

//Call normal function on instance of A.
A a;
a.bar();

//Call the static function on the class (rather than on an instance of the class). 
A::foo(); 

请注意,静态函数或数据成员是属于类本身的,无论您是否创建了该类的任何实例。因此,如果我的类中有一个静态变量,并创建了该类的一千个实例,那么该静态变量仍然只有一个实例。但是,将有 1000 个非静态成员的实例,每个类实例一个。

当您遇到它时,还有一个更有趣的选择:) 您还将看到:

//Create a pointer to a dynamically allocated A.
A* a = new A();

//Invoke/call bar through the pointer.
a->bar();

//Free the memory!!! 
delete a;

如果你还没有学过动态内存,可能会有点混乱,所以我不会详细介绍。只是想让您知道您可以使用 {或::}访问成员:).->

于 2012-07-11T22:14:55.437 回答
7

在 C++::中是范围解析运算符。它用于区分命名空间和静态方法,基本上任何情况下您都没有对象。Where.用于访问对象内部的东西。

C#.对它们都使用运算符。

namespace Foo
{
    public class Bar
    {          
        public void Method()
        {
        }

        public static void Instance()
        {
        }

    }
}

在 C# 中,您将编写如下代码:

var blah = new Foo.Bar();
blah.Method();

但等效的 C++ 代码看起来更像这样:

Foo::Bar blah;
blah.Method();

但请注意,静态方法也可以使用范围解析运算符访问,因为您没有引用对象。

Foo::Bar::Instance();

再说一次,C# 代码只会使用点运算符

Foo.Bar.Instance();
于 2012-07-11T22:15:09.757 回答
4

::用于命名空间和静态成员访问。C# 使用点运算符代替命名空间。

.用于非静态成员访问。

不是一个详尽的描述,但根据 C# 和 Java,相关位可能会让您感到困惑。

有关详细信息,请参阅

IBM - 范围解析运算符

IBM - 点运算符

于 2012-07-11T22:14:39.580 回答
2

::是范围解析运算符,因此当您解析范围(例如命名空间或类)时,您可以使用它。对于会员访问,您有.

于 2012-07-11T22:15:06.103 回答
1

::如果您不了解命名空间或类,则范围运算符可能难以理解。命名空间就像代码中各种事物名称的容器。它们通常用于消除库中常见的名称的歧义。说两个名称空间stdexample具有功能foobar()。所以编译器知道你想使用哪个函数,你把它添加为std::foobar()or 或example::foobar().

::当告诉编译器您要定义在类或结构中声明的函数时,也可以使用该运算符。例如:

class foobar()
{
  public:
  void hello();
  int number; //assume there is a constructor that sets this to 5
}

void foobar::hello()
{
  cout << "Hello, world!" << endl;
}

.您希望使用类或结构的成员时,使用运算符。例如:

foobar foo;
foo.hello();
cout << foo.number << endl;

假设类是通过编写构造函数来完成的,那么 this 的输出应该是:

Hello, world!
5
于 2012-07-11T22:29:49.007 回答
0

.在程序中创建类后访问类的成员时,您在 java 中使用相同的运算符。用于::多种情况:

当你在某个类的 .h/.cpp 中定义一个方法时,写

class::methodName()

要么是原型,要么是实现它。

此外,如果您没有明确说明使用的命名空间,则必须使用它

std::cout << "This is the output";

而不仅仅是使用cout << "This is the output;

也许还有更多,但我现在不记得了,我的 C++ 有点生锈了。

于 2012-07-11T22:17:39.633 回答
0

在 C++ 中,::用于标识范围。这可能意味着命名空间范围 类范围

例如。

int x;

namespace N {
    int x;

    struct foo {
        static double x;
        double y;    
    };
    struct bar: public foo {
        double y;
    };
}

int main()
{
    int x; // we have a local, hiding the global name
    x = ::x; // explicitly identify the x in global scope
    x += N::x; // explicitly identify the x in namespace N

    N::foo::x = x; // set the static member of foo to our local integer
    N::foo f;
    f.y = f.x; // the static member is implicitly scoped by the object
    f.y += N::foo::x; // or explicitly scoped

    N::bar b;
    assert(b.x == N::foo::x); // this static member is inherited
    b.y = b.x; // we get N::bar::y by default
    b.N::foo::y = b.y; // explicitly request the hidden inherited one
}

// we need to define the storage for that static somewhere too ...
int N::foo::x (0.0);
于 2012-07-11T22:29:16.107 回答