如何设置在console.log中返回的JavaScript对象名称?

时间:2022-08-27 18:08:57

So, first question here - please be gentle.

那么,首先要问一下 - 请保持温和。

I'm working on a fairly JavaScript heavy project with a few other developers from various non-web programming backgrounds and we've decided to try and use public and private methods and properties in our JavaScript psuedo-classes purely as a good coding practice (ie. we know theres no actual advantage or security in it)

我正在与一些来自各种非Web编程背景的其他开发人员合作开展一个相当重的JavaScript项目,我们决定尝试在我们的JavaScript伪类中使用公共和私有方法和属性,纯粹是一种良好的编码实践(即。我们知道它没有实际的优势或安全性)

We've toyed with a few different ways of doing public & private (ie. using locally scoped variables and functions with privileged methods for public consumption) and we've currently settled on having our JavaScript class constructors actually return an object that represents only their public interface, effectively hiding everything else.

我们玩弄了几种不同的公共和私有方式(即使用本地范围的变量和函数,使用特权方法进行公共消费),我们目前已经决定让我们的JavaScript类构造函数实际返回一个只代表他们的对象公共界面,有效隐藏其他一切。

Here's an example:

这是一个例子:

function MyObject()
 {
  var _this = this;

  this._privateProperty = 'somevalue';

  this._privateMethod = function()
  {
   // Do Something
  }

  this.public = 
  {
   publicProperty : _this._privateProperty,
   publicMethod : function(){ return _this.privateMethod() }
  }

  return this.public;
 }

Which when instantiated and logged in Chrome:

哪个在Chrome中实例化并登录时:

 var obj = new MyObject();
 console.log(obj);

Outputs:

> Object
    > publicMethod: function (){ return _this.privateMethod() }
    > publicProperty: "somevalue"
    >__proto__: Object

Now to my question: Because were returning the public interface from the constructor as new object, when you console.log you'll notice that it identifies itself as > Object - whereas if we don't return that public interface it is identified as > MyObject.

现在问我的问题:因为将构造函数中的公共接口作为新对象返回,所以当你在console.log中时,你会注意到它将自己标识为> Object - 而如果我们不返回该公共接口则将其标识为>为MyObject。

Ideally, we'd like to have the latter displayed for debugging purposes and I know how to access the "MyObject" name of the contstructor with _this.constructor.name, but have no idea how to set it so its recognized that way.

理想情况下,我们希望将后者显示用于调试目的,并且我知道如何使用_this.constructor.name访问contstructor的“MyObject”名称,但不知道如何设置它以使其以这种方式识别。

Does anyone know how to manually set this?

有谁知道如何手动设置这个?

Note:
I know this is in some ways a bastardization of JavaScript convention and trying to fit a square peg in a round hole, but we found it to be a very obvious and readable way to accomplish what we were trying to do. I'm open to suggestions on how to accomplish this with a different design, but I'm ultimately looking for an answer that fits our current design.

注意:我知道这在某些方面是JavaScript惯例的混乱,并试图在圆孔中安装方形挂钩,但我们发现它是一种非常明显和可读的方式来完成我们想要做的事情。我愿意接受有关如何使用不同设计实现此目的的建议,但我最终会寻找适合我们当前设计的答案。

3 个解决方案

#1


3  

You should be able to set the 'toString' function of the obj. E.g.

你应该能够设置obj的'toString'功能。例如。

obj.constructor.prototype.toString = function() { return "MyObject"; }

This will make the console.log display 'MyObject' instead of Object.

这将使console.log显示“MyObject”而不是Object。

#2


3  

Despite the valiant efforts of my team members and the very helpful users of this site who offered solutions we've decided that this design is ultimately unmaintainable and have instead opted for a design that is a little less obvious, but achieves the same result.

尽管我的团队成员以及本网站提供解决方案的非常有用的用户做出了勇敢的努力,但我们认为这种设计最终是不可维护的,而是选择了一个不太明显的设计,但实现了相同的结果。

function MyObject()
{
    var _privateProperty = 'somevalue';

    function _privateMethod()
    {
        // Do Something
    }

    // Public Interface
    this.publicProperty = _privateProperty;
    this.publicMethod = _privateMethod; 

}

With this approach we are basically making EVERY property and method private by default, and at the bottom of our "classes" we expose the ones we want available publicly. I think most would agree that this follows the normal JavaScript convention better than our initial design, which hopefully means it will be easier to read and maintain for others.

通过这种方法,我们基本上默认将每个属性和方法设为私有,并且在我们的“类”的底部,我们公开了我们想要公开的那些。我认为大多数人都同意这比普通的JavaScript惯例更符合我们的初始设计,这有望意味着它更容易阅读和维护。

Thanks again for those who took the time to try a come up with a solution.

再次感谢那些花时间尝试提出解决方案的人。

#3


1  

This is kind-of weird (but then, you're probably used to that by now :-) but you could override the actual "MyObject" constructor with a local one:

这有点奇怪(但是,你现在可能已经习惯了:-)但你可以用本地覆盖实际的“MyObject”构造函数:

function MyObject() {
  function MyObject(p) {
    for (var k in p) if (p.hasOwnProperty(k)) this[k] = p[k];
  }

  this.public = new MyObject({
    publicMethod: function() { /* whatever */ },
    publicProperty: "something"
  });
  return this.public;
}

Clearly you could factor out the code for most of that, so that you could have a function that, given a function to perform the initialization for a particular class, would set all that up for you. (Having to maintain a system like you're proposing without some library support to handle the details seems like a real chore, and long-term a very hard thing to keep working, and even harder to change.)

显然,您可以将大部分代码分解出来,这样您就可以拥有一个函数,给定一个执行特定类初始化的函数,将为您设置所有这些。 (必须维持一个类似于你提议的系统,如果没有一些图书馆支持来处理细节,这似乎是一项真正的苦差事,而长期是一件非常难以继续工作的事情,甚至更难改变。)

#1


3  

You should be able to set the 'toString' function of the obj. E.g.

你应该能够设置obj的'toString'功能。例如。

obj.constructor.prototype.toString = function() { return "MyObject"; }

This will make the console.log display 'MyObject' instead of Object.

这将使console.log显示“MyObject”而不是Object。

#2


3  

Despite the valiant efforts of my team members and the very helpful users of this site who offered solutions we've decided that this design is ultimately unmaintainable and have instead opted for a design that is a little less obvious, but achieves the same result.

尽管我的团队成员以及本网站提供解决方案的非常有用的用户做出了勇敢的努力,但我们认为这种设计最终是不可维护的,而是选择了一个不太明显的设计,但实现了相同的结果。

function MyObject()
{
    var _privateProperty = 'somevalue';

    function _privateMethod()
    {
        // Do Something
    }

    // Public Interface
    this.publicProperty = _privateProperty;
    this.publicMethod = _privateMethod; 

}

With this approach we are basically making EVERY property and method private by default, and at the bottom of our "classes" we expose the ones we want available publicly. I think most would agree that this follows the normal JavaScript convention better than our initial design, which hopefully means it will be easier to read and maintain for others.

通过这种方法,我们基本上默认将每个属性和方法设为私有,并且在我们的“类”的底部,我们公开了我们想要公开的那些。我认为大多数人都同意这比普通的JavaScript惯例更符合我们的初始设计,这有望意味着它更容易阅读和维护。

Thanks again for those who took the time to try a come up with a solution.

再次感谢那些花时间尝试提出解决方案的人。

#3


1  

This is kind-of weird (but then, you're probably used to that by now :-) but you could override the actual "MyObject" constructor with a local one:

这有点奇怪(但是,你现在可能已经习惯了:-)但你可以用本地覆盖实际的“MyObject”构造函数:

function MyObject() {
  function MyObject(p) {
    for (var k in p) if (p.hasOwnProperty(k)) this[k] = p[k];
  }

  this.public = new MyObject({
    publicMethod: function() { /* whatever */ },
    publicProperty: "something"
  });
  return this.public;
}

Clearly you could factor out the code for most of that, so that you could have a function that, given a function to perform the initialization for a particular class, would set all that up for you. (Having to maintain a system like you're proposing without some library support to handle the details seems like a real chore, and long-term a very hard thing to keep working, and even harder to change.)

显然,您可以将大部分代码分解出来,这样您就可以拥有一个函数,给定一个执行特定类初始化的函数,将为您设置所有这些。 (必须维持一个类似于你提议的系统,如果没有一些图书馆支持来处理细节,这似乎是一项真正的苦差事,而长期是一件非常难以继续工作的事情,甚至更难改变。)