skip to Main Content

I’ve been learning JavaScript for some time and so far I haven’t encountered almost any problems.

Today I was studying the part related to getters and setters on objects and, when I started "revising" the topic, writing code on Visual Studio Code, I ran into this problem:

Uncaught RangeError: Maximum call stack size exceeded on "age" property

This is the code I’ve written so far:

let user = {
    name: "Fra",
    surname: "Emme",

    set age(value) {
        if (value < 18) {
            console.log(`${value} - You are underage :(`);
        } else {
            this.age = value;
        }
    },

    get fullName() {
        return `${this.name} ${this.surname}`;
    },

    set place(value) {
        if (value === "" || value === null || value.length <= 2) {
            console.log("Invalid place");
            return;
        }
        this.place = value;
    }
};

user.age = 20;
user.place = "Rovereto";

console.log(user);

I’ve searched the internet a bit, but all I find are solutions to problems related to recursion.

Could someone help me to solve the problem? So I also understand where I went wrong (if I was wrong).

Thanks in advance to everyone!

2

Answers


  1. user.age = 20 calls the set age(value) setter function. The set age(value) setter function then has the statement this.age = value which ends up calling the set age(value) setter function. Repeat this step until the max stack error you encountered. Consider setting an "internal" property, often conventionally indicated by an underscore (_) prefix:

    let user = {
        name: "Fra",
        surname: "Emme",
    
        set age(value) {
            if (value < 18) {
                console.log(`${value} - You are underage :(`);
            } else {
                this._age = value;
            }
        },
    
        get age() {
          return this._age;
        },
    
        get fullName() {
            return `${this.name} ${this.surname}`;
        },
    
        set place(value) {
            if (value === "" || value === null || value.length <= 2) {
                console.log("Invalid place");
                return;
            }
            this._place = value;
        },
    
        get place() {
          return this._place;
        },
    };
    
    user.age = 20;
    user.place = "Rovereto";
    
    console.log(user);
    Login or Signup to reply.
  2. In your setter for age your are setting age -> endless loop.
    In your setter for place you are setting place -> endless loop.

    Remember: You have created a setter – it will be called each time you set a new value to it. 🙂

    If this was a class I would advice you to you use private members for storing the real values, since it isn’t I’ve created two new properties _age and _place that we can use to store the values of age and place…

    Here’s the revised code:

    let user = {
      name: "Fra",
      surname: "Emme",
    
      _age: 0,
      _place: '',
    
      set age(value) {
        if (value < 18) {
          console.log(`${value} - You are underage :(`);
        } else {
          this._age = value;
        }
      },
    
      get age() {
        return this._age;
      },
    
      get fullName() {
        return `${this.name} ${this.surname}`;
      },
    
      set place(value) {
        if (value === "" || value === null || value.length <= 2) {
          console.log("Invalid place");
          return;
        }
        this._place = value;
      },
    
      get place() {
        return this._place;
      }
    };
    
    user.age = 20;
    user.place = "Rovereto";
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search