Javascript 如果此参数为';他被认为是私人的

Javascript 如果此参数为';他被认为是私人的,javascript,closures,Javascript,Closures,关于私有变量封装——通过将私有变量定义为var,而不是this(非private this.private)的属性来实现。这是使成员私有化的最直接的方法 但是,如果正在返回并使用实例,则上述规则是有意义的。在这种情况下,我们返回一个新对象,并公开get/set方法。现在,将私有变量存储在thisparam中是否仍然实现了私有变量封装 当实例参数没有被返回时,有什么方法可以访问它吗 function X(init) { this.private = init; var that = th

关于私有变量封装——通过将私有变量定义为
var
,而不是
this
(非private this.private)的属性来实现。这是使成员私有化的最直接的方法

但是,如果正在返回并使用实例,则上述规则是有意义的。在这种情况下,我们返回一个新对象,并公开get/set方法。现在,将私有变量存储在
this
param中是否仍然实现了私有变量封装

当实例参数没有被返回时,有什么方法可以访问它吗

function X(init) {
  this.private = init; 
  var that = this
  function get() {
    return that.private;
  }

  function set (tmp) {
    that.private = tmp;
  }

  return {
    get: get,
    set: set
  }
}

var tmp = new X(1);

console.log(tmp.get()) // 1

console.log(tmp instanceof X) // false

tmp.private = 20 // doesnt work as tmp isnt an instance object

console.log(x.get()) //1

x.set(20)

console.log(x.get()) //20

当未返回
时,我是否可以访问private,因为它是
的属性?

您可以使用WeakMap实现真正的隐私。
function X(init) {
  this.private = init; 
  var that = this
  function get() {
    return that.private;
  }

  function set (tmp) {
    that.private = tmp;
  }

  return {
    get: get,
    set: set
  }
}

var tmp = new X(1);

console.log(tmp.get()) // 1

console.log(tmp instanceof X) // false

tmp.private = 20 // doesnt work as tmp isnt an instance object

console.log(x.get()) //1

x.set(20)

console.log(x.get()) //20

WeakMaps允许您创建附属对象,您可以在其上附加任何值。 如果无法访问定义它们的范围,则无法访问它们

在浏览器中使用ES5

"use strict";
{
    const privacy = new WeakMap();

    function X(init)
    {
        privacy.set(this, {});

        const props = privacy.get(this);

        props.init = init;
    }

    X.prototype.setInit = function(tmp)
    {
        privacy.get(this).init = tmp;
    };

    X.prototype.getInit = function()
    {
        return privacy.get(this).init;
    };

    window.X = X;
}
在NodeJS中使用ES6类表示法

const privacy = new WeakMap();

class X
{
    constructor(init)
    {
        privacy.set(this, {});

        const props = privacy.get(this);

        props.init = init;
    }

    setInit(tmp)
    {
        privacy.get(this).init = tmp;
    }

    getInit()
    {
        return privacy.get(this).init;
    }
}

module.exports = X;

不,我们无法访问此属性的private,因为您显式返回新对象。

使用构造函数时,请考虑以下示例:

function X()
{
   // Scope of X()
   var i = 1; // this variable is accessible only in this scope
   this.get = function() { return i; };
}

a = new X(); // call the constructor
console.log(a.i); // this will be undefined
a.i = 2; // even if you try to set `i` on `a`

console.log(a.get()); // the actual `i` of `a` will still be 1
console.log(a.i); // this will be two.
现在来看使用函数返回对象的示例

function Y()
{
    // Scope of Y()
    var i = 1; // this variable is accessible only in this scope
    function get() { return i; };

    return { // now you return an object which exposes a function that returns the value of `i` of this SCOPE.
        get: get
    }
}

b = Y();

console.log(b.i); // this will be undefined
console.log(b.get()); // this will be 1
b.i = 3; // this will work
console.log(b.get()); // this will still be 1
console.log(b.i); // this will be 3
很抱歉,我没有足够的时间继续解释,稍后我会再讨论这个问题

通过将成员变量隐藏在作用域中,可以隐藏(使其成为私有)成员变量


此外,在这两种方法之间,只有第一种方法可以使用
this
关键字。您不能在第二种方法中使用
关键字,因为它的值将是窗口

“此参数”。参数是函数的参数。你想说的是属性。你的函数返回一个对象,而你却把它用作构造函数。@StefanOctavian更新了。@Wreigh只是一个示例代码。downvoter?这是一个多么糟糕的问题?我真的不知道我是否可以访问这个参数!这并没有回答我的问题我的问题是,当
{get:get}
被返回时,我是否有权访问实例(
this
)变量。请检查给定的示例。没有,因为您返回了一个全新的对象,即使您使用了
new
。阅读我的最新更新,
仅在创建对象时使用了
new
关键字时可用。在你的例子中,是的,你使用了
new
关键字,但是你返回了一个不同的对象。我的想法正是如此。想确保没有办法访问它。