# init static property

[JS](/web/js.md) ⟩ [value](/web/js/val.md) ⟩ [object](/web/js/val/obj.md) ⟩ [class](/web/js/val/class.md) ⟩ [member](/web/js/val/class/member.md) ⟩ [static](/web/js/val/class/member/static.md) ⟩ init&#x20;

{% hint style="info" %}
本篇討論： [#how-to](#how-to "mention")
{% endhint %}

{% tabs %}
{% tab title="👥 相關" %}

* [static block](/web/js/val/class/init/init.md)：用於對 [static property](/web/js/val/class/member/static.md) 的初始化
* [web component](/web/component.md)：可用這裡的方法初始化 component 的靜態屬性
  {% endtab %}

{% tab title="💾 程式" %}
⭐️ static members

{% hint style="warning" %}
:star: 注意：<mark style="color:yellow;">static getter</mark> <mark style="color:blue;">`static get c() {}`</mark> <mark style="color:red;">不能省略</mark> <mark style="color:blue;">`get`</mark>，不然會變成 <mark style="color:yellow;">static method</mark> <mark style="color:blue;">`static c() {}`</mark>:exclamation:
{% endhint %}

```javascript
class A {
  static a;                 // A.a = undefined
  static b = 0;             // A.b   (static property: initialized)
  static get c() { ... }    // A.c   (static getter)
  static d() { ... }        // A.d() (static method)
}
```

⭐️ private static members

{% hint style="warning" %}

* accessable <mark style="color:yellow;">only within the class body</mark>.
* private members are <mark style="color:yellow;">not inherited</mark>.
  {% endhint %}

```javascript
class A {
  // ⭐️ "#" means "private"
  static #e;                // A.#e    (private static property: uninitialized)
  static get #f() { ... }   // A.#f    (private static getter)
  static #g() { ... }       // A.#g()  (private static method)
}
```

{% endtab %}

{% tab title="📘 手冊" %}

* MDN ⟩ [JavaScript](https://developer.mozilla.org/en-US/docs/Web/JavaScript) ⟩ [Reference](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference) ⟩ [Classes](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes) ⟩&#x20;
  * [static](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes/static)
  * [Static initialization blocks](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes/Static_initialization_blocks)
    {% endtab %}

{% tab title="📗 參考" %}

* [ ] [JS.info ⟩ class ⟩ Static properties and methods](https://javascript.info/static-properties-methods)
* [ ] ChatGPT ⟩ [static property init](https://chatgpt.com/share/676ccd2d-bc5c-800e-bb4a-9ec7c4fb546f)&#x20;
  {% endtab %}
  {% endtabs %}

## 如何初始化靜態屬性 <a href="#how-to" id="how-to"></a>

{% tabs %}
{% tab title="⚖️ 比較" %}

<table><thead><tr><th width="79" align="center">方法</th><th width="84" align="center">推薦</th><th>優點</th><th>缺點</th></tr></thead><tbody><tr><td align="center">1</td><td align="center"><span data-gb-custom-inline data-tag="emoji" data-code="1f44d">👍</span></td><td>✅ 延遲初始化</td><td><span data-gb-custom-inline data-tag="emoji" data-code="26a0">⚠️</span> 額外的私有靜態屬性</td></tr><tr><td align="center">2</td><td align="center"></td><td></td><td><span data-gb-custom-inline data-tag="emoji" data-code="26a0">⚠️</span> 不夠模組化</td></tr><tr><td align="center">3</td><td align="center"><span data-gb-custom-inline data-tag="emoji" data-code="1f44d">👍</span></td><td>✅ 模組化</td><td><span data-gb-custom-inline data-tag="emoji" data-code="26a0">⚠️</span> <mark style="color:orange;">ES2022</mark></td></tr><tr><td align="center">4</td><td align="center"></td><td>✅ 模組化</td><td></td></tr></tbody></table>
{% endtab %}

{% tab title="1" %}
方法一：使用 [static](/web/js/val/class/member/static.md) [getter](/web/js/val/class/member/getter-setter.md)

```javascript
class ClassA {
	
	// ClassA.CONSTANT
	// 方法一：使用 static getter（傳回 ClassA._CONSTANT 的值）
	// • 優點：
	//   ✅ 延遲初始化 
	// • 缺點：
	//   ❗ 額外的私有靜態屬性 (ClassA._CONSTANT)
	// ⭐️ 注意：不能省略 `get`，不然會變成 static method❗
	static get CONSTANT() {
		
		// 如果還沒初始化
		// ⭐️ in static method/block/getter, this == class itself.
		if (!this._CONSTANT) {
			// 執行初始化 ...，然後將結果存在私有靜態屬性中
			this._CONSTANT = 100; 
		}
		
		return this._CONSTANT;
	}
	
}
```

{% endtab %}

{% tab title="2" %}
方法二：在 class 定義後立即計算賦值

```javascript
class ClassB {
  	// ClassB.CONSTANT
	// 方法二：在 class 定義後立即計算賦值
	// • 缺點：
	//   ❗程式碼不夠模組化
	static CONSTANT;	// 1. 先宣告
}

// block
{
	// 複雜的初始化邏輯 ...
	ClassB.CONSTANT = 200;	// 2. 後面立即計算賦值
}
```

{% endtab %}

{% tab title="3" %}
方法三：使用 [static block](/web/js/val/class/init/init.md) (<mark style="color:orange;">ES2022</mark>)（<mark style="color:yellow;">方法二的現代版</mark>）

```javascript
class ClassC {
	
	// ClassC.CONSTANT  
	// 方法三：使用 static block (ES2022)（方法二的現代版）
	// • 優點：
	//   ✅ 模組化（沒有程式碼外漏於 class 定義外）
	//   ✅ 語法簡潔，不需外部的計算(方法二)、或內部的靜態方法(方法四)
	static CONSTANT;			// 1. 先宣告
	  
	// ⭐️ static block (ES2022)
	// ⭐️ in static method/block/getter, this == class itself.
	static {						
		// 複雜的初始化邏輯 ...
		this.CONSTANT = 300;		// 2. 後面立即計算賦值
	}
}
```

{% endtab %}

{% tab title="4" %}
方法四：使用 [static method](/web/js/val/builtin/arr/static-methods.md) 賦值

```javascript
class ClassD {
  
	// ClassD.CONSTANT
	// 方法四：使用 static method 賦值
	// • ✅ 優點：模組化（沒有程式碼外漏於 class 定義外）
	// ⭐️ in static method/block/getter/declaration, this == class itself.
	static CONSTANT = this.initStaticConstant();

	static initStaticConstant() {
    	// 複雜的初始化邏輯 ...
		return 400;
	}
}
```

{% endtab %}

{% tab title="💈範例" %}

* codepen ⟩ [static property init](https://codepen.io/pegasusroe/pen/JoPJQXp)&#x20;
  {% endtab %}
  {% endtabs %}


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://lochiwei.gitbook.io/web/js/val/class/member/static/init.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
