質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.47%
JavaScript

JavaScriptは、プログラミング言語のひとつです。ネットスケープコミュニケーションズで開発されました。 開発当初はLiveScriptと呼ばれていましたが、業務提携していたサン・マイクロシステムズが開発したJavaが脚光を浴びていたことから、JavaScriptと改名されました。 動きのあるWebページを作ることを目的に開発されたもので、主要なWebブラウザのほとんどに搭載されています。

Q&A

解決済

3回答

1315閲覧

Object.assign について

退会済みユーザー

退会済みユーザー

総合スコア0

JavaScript

JavaScriptは、プログラミング言語のひとつです。ネットスケープコミュニケーションズで開発されました。 開発当初はLiveScriptと呼ばれていましたが、業務提携していたサン・マイクロシステムズが開発したJavaが脚光を浴びていたことから、JavaScriptと改名されました。 動きのあるWebページを作ることを目的に開発されたもので、主要なWebブラウザのほとんどに搭載されています。

0グッド

1クリップ

投稿2021/05/27 11:52

js

1const defaultOptions = { 2 a: true, 3 b: false, 4 c: { 5 a: true, 6 b: true 7 } 8}; 9const yourOptions = { 10 a: false, 11 c: { 12 b: false 13 } 14}; 15const options = Object.assign(defaultOptions, yourOptions); 16console.log(options.c.a); // undefined

Object.assignメソッドでは第一階層にあるJSONのみを上書きできるのでしょうか?
上記のソースコードを実行するとその階層以降(defaultOptions.c)の中身は全てコピーされません。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答3

0

MDN - Object.assign

こちらを読んで頂いて、 Object.assign の第一引数の値も書き換えられていることに注意してください。
今回のケースでも defaultOptions は上書きされています。 console.log(defaultOptions) で確認してみてください。
上書きしたくない場合は Object.assign({}, defaultOptions, yourOptions) などを使いましょう。

深いコピーに関しても注意書きがあります。
深い複製についての注意

投稿2021/05/27 13:07

mather

総合スコア6753

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

上記のソースコードを実行するとその階層以降(defaultOptions.c)の中身は全てコピーされません。

いえ、逆にyourOptions.cがコピーされて、そちらで上書きされています

投稿2021/05/27 12:01

maisumakun

総合スコア145201

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

退会済みユーザー

退会済みユーザー

2021/05/27 12:55 編集

コート上では見えないですけど yourOptions.c.a は undefined と定義している感じで、それがそのまま上書きされてる感じですかね?
maisumakun

2021/05/27 12:14

ではないです。options.cは、yourOptions.cと同一のオブジェクトです。 「options.c.a」のように存在しないプロパティにアクセスしてもJavaScriptではエラーにならず、ただundefinedを返します。
退会済みユーザー

退会済みユーザー

2021/05/27 12:58

ありがとうございます。大体理解できました。 こういったデータの上書きは Object.assign 単体では難しいと考えられますが、何か良い方法は無いのでしょうかね? 海外の似たような質問の回答だとfor文とかいろいろ複雑なコードを見つけましたが(^^;
maisumakun

2021/05/27 13:01

ライブラリはちょくちょく見つかりますので、探してなにか取り入れてみるのもありかもしれません。
guest

0

ベストアンサー

js

1function newAssign(target, ...sources) { 2 sources.forEach((source) => { 3 const descriptors = Object.keys(source).reduce((descriptors, key) => { 4 const descriptor = Object.getOwnPropertyDescriptor(source, key); 5 const value = descriptor.value; 6 if (typeof value == "object") { 7 newAssign(target[key], value); 8 } else { 9 descriptors[key] = descriptor; 10 } 11 return descriptors; 12 }, {}); 13 Object.defineProperties(target, descriptors); 14 }); 15 return target; 16} 17 18const defaultOptions = { 19 a: true, 20 b: false, 21 c: { 22 a: true, 23 b: true, 24 c: { 25 b: false, 26 }, 27 d: { 28 a: [0, 2, 3] 29 } 30 } 31}; 32const yourOptions = { 33 a: false, 34 c: { 35 b: false, 36 c: { 37 a: true 38 } 39 } 40}; 41const options = newAssign(defaultOptions, yourOptions); 42console.log(options);

とりあえず、いろいろ情報を整理してこんな感じのコードで自分のやりたいことはできました。
自分用なので不要な部分があったり、値の構造によってはエラーが発生してしまいますが...
とりあえず解決したことを報告させていただきます。皆様ありがとうございました。

投稿2021/05/27 22:24

編集2021/05/27 22:27
退会済みユーザー

退会済みユーザー

総合スコア0

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.47%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問