`
lovelium
  • 浏览: 18887 次
  • 性别: Icon_minigender_1
  • 来自: 广州
最近访客 更多访客>>
社区版块
存档分类
最新评论

JavaScript中的私有成员

阅读更多
 本文地址:http://www.nirvanastudio.org/javascript/private-members-in-javascript.html

Douglas Crockford www.crockford.com

翻译:ShiningRay @ Nirvana Studio

JavaScript 是世界上最被误解的语言。很多人认为它缺乏信息隐藏的特性所以对象不能有私有实例变量和方法。但这是一个误解。JavaScript对象同样可以拥有私有变量。下面就讲解一下:

对象

JavaScript根本上都是关于的对象(Object)的。数组(Array)是对象,函数(Function)是对象,Object就不说 了。那什么是对象?对象是名称-值的配对的集合。名称是字符串,值可以是字符串、数字、布尔值和对象(包括数组和函数)。对象常常实现为哈希表以快速存取 值。

如果一个值是函数,我们可以将它视为方法method。当调用一个对象的方法时,this 变量就会被设为该对象。这个方法就可以通过this变量访问实例变量。

对象是由构造器constructor产生的,它是初始化对象的函数。构造器提供了其它语言中类提供的特性,包括静态方法和变量。

公共成员

对象的成员都是 public 公共成员。任何函数都可以访问、修改或者删除这些成员。有两种主要的途径给新的对象加入成员:

构造器中

这个技术一般用来初始化公共实例变量。构造器的this变量是用来向对象添加成员的。

function Container(param) {    this.member = param;}
这样,如果我们构造一个新的对象
var myContainer = new Container('abc');
那么myContainer.member 就会包含'abc'

原型中

这个技巧一般用来添加公共方法。当一个成员被检索且没有在对象中发现的时候,那么它就会从对象构造器的 prototype 成员中去获取它。这个原型机制可用来实现继承。它也保存内存。要为一个构造器生成的所有对象加入一个方法,将函数加入构造器的prototype 中:

Container.prototype.stamp = function (string) {
return this.member + string;
}
这样,我们可以调用这个方法
myContainer.stamp('def')
它会返回'abcdef'.

私有成员

私有Private成员要由构造器生成。构造器中的普通的var变量和参数都成为私有成员。

function Container(param) {
this.member = param;
var secret = 3;
var self = this;}

这个构造器有三个私有实例变量:param, secret, 和 self。它们被附加到了对象上,但它们无法从外部访问,同时它们也无法被这个对象的公共方法所访问。他们只对私有成员可见。私有方法则是构造器内部的函数。

function Container(param) {

function dec() {
if (secret > 0) {
secret -= 1;
return true;
} else {
return false;
}
}

this.member = param;
var secret = 3;
var self = this;
}

私有方法 dec 检查 secret 实例变量。如果它大于0,就减少secret 的大小并返回 true 。否则它返回 false 。这个可以限制对象使用三次。

按照惯例,我们给出一个私有的 self 参数。这个可以令对象对私有方法可见。这种做法是因为ECMAScript Language Specification中的一个错误,这个错误令 this 不能正确地对内部函数设置。

私有方法无法被公共方法调用。要令私有方法有用,我们需要引入一种特权方法。

特权成员

一个特权A privileged 方法可以访问私有的变量和方法,同时它对公共域可见。也可以删除或替换一个特权方法,但不能改变它。

特权方法是用 this 在构造器中分配的。

function Container(param) {

function dec() {
if (secret > 0) {
secret -= 1;
return true;
} else {
return false;
}
}

this.member = param;
var secret = 3;
var self = this;

this.service = function () {
if (dec()) {
return self.member;
} else {
return null;
}
};
}

service 就是一个特权方法。前三次调用会返回'abc'。 之后 ,它会返回 nullservice调用的私有的 dec 方法,而 dec又访问了私有的 secret变量。service对其它的对象和方法是可见的,但不能直接访问私有成员。

闭包

这种公共、私有和特权成员的模式是可行的原因是由于JavaScript有 closure闭包。这个意味着一个内部的函数总是可以访问这个函数外部的变量和参数,甚至在外部的函数返回之后。这是这个语言的一个极其强大的特性。目前没有哪本关于JavaScript编程的书展示了如何发掘这个特性。大多数都没有提到。

私有和特权成员只能在对象构造的时候生成。公共成员可以在任意时刻添加。

模式

公共(Public)

function Constructor(...) {
this.membername = value;
}
Constructor.prototype.membername = value;

私有(Private)

function Constructor(...) {  
var self = this;
var membername = value;
function membername(...) {...}
}
注意,实际上函数语句
function  membername(...)  {...}
是以下语句的缩写,两者相同:
var  membername = function  membername(...)  {...};

特权(Privileged)

function Constructor(...) {  
this.membername = function (...) {...};
}
Copyright 2001 Douglas Crockford. All Rights Reserved Wrrrldwide.

4 Responses to “JavaScript中的私有成员”

  1. Fantasy Says:

    这个构造器有三个私有实例变量:param, secret, 和 self。它们被附加到了对象上,但它们无法从外部访问,同时它们也无法被这个对象的公共方法所访问。他们只对私有成员可见。私有方法则是构造器内部的函数。

    不对把~~~~~~~~~~~~~

    function MyClass()
    {
    var name = “QQ”;
    this.getName = function()
    {
    return name;
    }
    }

    var myClass = new MyClass();

    alert(myClass.getName());

    难道取不到 name ?????????????

  2. ShiningRay Says:

    楼上的兄弟,其实是阅读的上下文的问题,说这句话的时候是指,如果仅仅使用这个构造器:
    function Container(param) { this.member = param; var secret = 3; var self = this;}
    那么param, secret和self确实无法从外部访问。

  3. liwei Says:

    1楼的兄弟是不是还没有看完文章就写的评论啊。
    人家下面不是说了
    this.getName = function()
    {
    return name;
    }
    这样的算做 “特权方法”嘛。

  4. Lich_Ray Says:

    1楼的兄弟确实那个~~
    其实没必要强调“特权方法”,函数即对象,只是可执行而已;所谓的“私有”其实源于JavaScript中函数名字空间的临时性,不值得专门拿出来讲。

分享到:
评论

相关推荐

    探索JavaScript中私有成员的相关知识

    在JavaScript中,私有成员指的是那些只能在定义它们的类内部访问的成员,通常包括私有变量和私有方法。虽然JavaScript本身并不直接支持私有成员,但可以通过一些技巧来模拟实现。本文将深入探讨如何在JavaScript中...

    如何在JavaScript对象中嵌入私有成员.doc

    在JavaScript中,创建私有成员通常是为了保护对象的内部状态,防止外部代码直接访问或修改。这在构建复杂的模块或类时尤其重要,因为它有助于确保数据的安全性和代码的封装性。在JavaScript中,由于其动态类型和全局...

    JavaScript 面向对象的 私有成员和公开成员

    在JavaScript中,虽然没有正式的private和public关键字来定义私有和公开成员,但是通过特定的编码约定和模式,我们可以模拟实现私有成员和公开成员的概念。 私有成员和公开成员是面向对象编程(OOP)中的基本概念。...

    JavaScript之私有属性,私有函数,函数实现对外不可见

    在JavaScript编程中,私有...通过合理地设计私有成员和公共接口,我们可以确保对象的状态正确被管理,同时防止意外的副作用。在实际开发中,应根据项目需求和团队规范灵活运用这些技术,以实现最佳的代码结构和功能。

    JavaScript 私有成员分析

    JavaScript是世界上最受误解的语言。有人认为它缺少信息隐藏的属性(封装),因为JavaScript对象不能拥有私有变量和函数。但这是误解。JavaScript对象可以有私有成员。下面进行说明。

    JavaScript 面向对象的之私有成员和公开成员

    在JavaScript中,通过以下几种方式可以创建私有成员: 1. 使用函数作用域:在构造函数内部使用var关键字声明的变量或函数可以视为私有成员,因为它们只在构造函数内部可见。例如: ```javascript var MyClass = ...

    Javascript 构造函数,公有,私有特权和静态成员定义方法

    构造函数中的成员可以被分为公有成员和私有成员。公有成员指的是那些可以被对象外部访问的属性和方法,而私有成员则是只能在对象内部访问的属性和方法。通常,私有成员可以用来存储一些对象不需要直接访问的数据,...

    Javascript类定义语法,私有成员、受保护成员、静态成员等介绍

    为了弥补这一不足,JavaScript允许我们使用类的语法糖,以支持类定义和模拟面向对象编程语言中的成员访问控制,包括私有成员、受保护成员和静态成员。 在JavaScript中,类的定义往往基于构造函数或者使用ES6引入的...

    javascript-private-variables:JavaScript的私有成员变量,在“编译时”

    通常,开发人员会在某些成员变量之前加下划线,以表示它们是“私有”的。 但是,下划线本身对所有JavaScript解释器几乎毫无意义,因此,没有办法知道是否存在对“私有”变量的任何非法访问。 使用此ESLint插件,...

    JavaScript中的公有、私有、特权和静态成员用法分析

    其次,私有成员在JavaScript中的定义与其他传统面向对象编程语言有所不同。由于JavaScript没有严格的访问控制关键字(如Java中的private),因此私有属性和方法通常以变量和函数的形式定义在构造函数内部,但不在...

    Node.js-private-class保护类私有属性的一个模块

    `private-class`模块就是为了解决JavaScript中缺乏原生私有成员支持的问题。 在Node.js中,通常我们使用ES6的类语法来定义一个类: ```javascript class MyClass { constructor() { // ... } publicMethod() ...

Global site tag (gtag.js) - Google Analytics