Noh | エンジニア向け情報共有コミュニティ
Signup / Login

[JS] Overrideしたときの挙動が異なる

y
yosi2024/09/10 22:19

以下のクラスとそれを呼びだすコードがあります。

import * as THREE from "three" import { VRMLookAt } from "@pixiv/three-vrm" const _v3A = new THREE.Vector3() export class CustomVRMLookAt extends VRMLookAt { constructor(humanoid: any, applier: any) { super(humanoid, applier) } public update(delta: number): void { if (this.target != null && this.autoUpdate) { this.lookAt(this.target.getWorldPosition(_v3A)) } if (this._needsUpdate) { this._needsUpdate = false this.applier.applyYawPitch(this._yaw, this._pitch) } } }
const vrmLookAt = new CustomVRMLookAt(vrm.humanoid, vrm.lookAt.applier) vrmLookAt.copy(vrm.lookAt) vrm.lookAt = vrmLookAt vrm.lookAt.target = camera vrm.update(1)

このとき、updateの実行をさせないために以下の変更を加えた時をAとします。

public update(delta: number): void { // if (this.target != null && this.autoUpdate) { // this.lookAt(this.target.getWorldPosition(_v3A)) // } // if (this._needsUpdate) { // this._needsUpdate = false // this.applier.applyYawPitch(this._yaw, this._pitch) // } }

また、updateの実行をさせないために以下の変更を加えた時をBとします。

const vrmLookAt = new CustomVRMLookAt(vrm.humanoid, vrm.lookAt.applier) vrmLookAt.copy(vrm.lookAt) vrm.lookAt = vrmLookAt vrm.lookAt.target = camera // vrm.update(1)

AとBはどちらもupdateの内容を実行させない変更ですが、挙動が異なります。
どういった原因が考えられますか。

A
Answerer AIPowered by gpt-3.5-turbo

AとBの変更は、どちらもupdateメソッドを実行しないため、updateメソッドの内容が実行されないという点では同じです。しかし、挙動が異なる原因は、updateメソッド内のコードが異なるためです。

Aの場合、updateメソッド内では、this.targetが存在し、かつthis.autoUpdatetrueの場合にのみ、lookAtメソッドとapplier.applyYawPitchメソッドが呼ばれます。

一方、Bの場合、updateメソッドが全てコメントアウトされているため、lookAtメソッドとapplier.applyYawPitchメソッドは全く実行されません。

結果的に、AではlookAtメソッドとapplier.applyYawPitchメソッドは呼ばれないが、Bでは全く実行されないため、挙動が異なるということになります。

y
yosi2024/09/10 22:21

最終的な実行結果はAとBで同じになるはずですが、そうなりません。

A
Answerer AIPowered by gpt-3.5-turbo

申し訳ありません、誤解の解消ができていなかったようです。

実行結果が異なるのは、updateメソッドが実行されないためではなく、vrm.update(1)の呼び出しの有無によるものです。つまり、AでもBでもvrm.update(1)を実行しない場合には、updateメソッドが呼び出されないため、処理内容による影響がありません。

もしもAとBで実行結果が異なるならば、それはvrm.update(1)が影響を与えている可能性があります。vrm.update(1)によって、vrmオブジェクトやその内部の状態が変化することで、結果が異なることがあります。

この場合、vrm.update(1)を実行した際に、updateメソッド内の処理が実行されて、その結果が異なる可能性があります。具体的にどのような変化が起きるかは、updateメソッド内のコードやvrmオブジェクトの実装に依存します。

したがって、実行結果がAとBで異なる場合、vrm.update(1)の実行が原因であると考えられます。vrm.update(1)の挙動を確認して、その結果を分析することで、原因を特定できるかもしれません。

y
yosi2024/09/10 22:25

JSで継承元クラスのメソッドをオーバーライドしたとき、オーバーライドされたメソッドの処理が実行されることはありますか。

A
Answerer AIPowered by gpt-3.5-turbo

はい、JavaScriptにおいて継承元クラスのメソッドをオーバーライドすると、オーバーライドされたメソッドの処理が実行されるようになります。

継承元クラスのメソッドをオーバーライドすると、サブクラスで同じ名前のメソッドを定義することができます。そして、そのメソッドが呼び出された場合には、サブクラスで定義されたメソッドが実行されます。

ただし、サブクラスでオーバーライドしたメソッド内で、継承元クラスの同じ名前のメソッドを呼び出したい場合は、「super」キーワードを使用することができます。これにより、オーバーライドされたメソッドと継承元クラスのメソッドの両方の処理を実行することができます。

具体的なコード例を示します。

class Parent { method() { console.log("Parent's method"); } } class Child extends Parent { method() { super.method(); // 継承元クラスのメソッドを呼び出し console.log("Child's method"); } } const obj = new Child(); obj.method(); // 出力: "Parent's method" と "Child's method"

上記の例では、Childクラスでmethodメソッドをオーバーライドしています。そのため、Childクラスのmethodメソッドが呼び出された際には、継承元クラスのParentクラスのmethodメソッドと、Childクラスのmethodメソッドの両方の処理が実行されます。

y
yosi2024/09/10 22:31

寝ぼけていた。。。

updateは異なるクラスのメソッドだった。

コメントするにはログインが必要です
y
yosi