teratail header banner
teratail header banner
質問するログイン新規登録

回答編集履歴

7

コードの挙動について修正

2019/09/04 03:24

投稿

frodo821
frodo821

スコア322

answer CHANGED
@@ -93,7 +93,7 @@
93
93
 
94
94
  let ins = new Test(5);
95
95
  ins.func() // -> 5
96
- (0, ins.func)() // -> undefined
96
+ (0, ins.func)() // -> TypeError: Cannot read property 'x' of undefined
97
97
  ins.func1() // -> 5
98
98
  (0, ins.func1)() // -> 5
99
99
  ```

6

コードの整形

2019/09/04 03:24

投稿

frodo821
frodo821

スコア322

answer CHANGED
@@ -6,7 +6,7 @@
6
6
  return database.find(el => el.id === id)
7
7
  },
8
8
  asyncFind(id) {
9
- return new Promise((res, rej) => setTimeout(() => {
9
+ return new Promise(res => setTimeout(() => {
10
10
  res(this.find(id))
11
11
  }, 1000))
12
12
  }
@@ -32,7 +32,7 @@
32
32
  handler() {
33
33
  products
34
34
  .asyncFind(this.id)
35
- .then(it => this.items = it);
35
+ .then(it => this.item = it);
36
36
  },
37
37
  immediate: true
38
38
  }

5

誤字修正

2019/08/31 21:39

投稿

frodo821
frodo821

スコア322

answer CHANGED
@@ -78,7 +78,7 @@
78
78
 
79
79
  他方、3と4の戻り値は共に5となります。なぜなら、定義された場所のthis.xは5だからです。定義された場所とは、自分自身を格納しているオブジェクトの中を__意味しません__。そのオブジェクトが定義された場所こそがthisの指し示す先になります。
80
80
 
81
- そこで、新しいクラスの宣言方法では、インスタンスから直接呼ばない関数はArrow関数式で記述します。なぜなら、既存の無名関数式ではインスタンスから直接呼ばなければ、thisの示す先がインスタンスではなくなってしまうからです。一方Arrow関数式は想定された挙動をする、つまり直接呼ばなくてもthisはインスタンスを示すからです
81
+ そこで、新しいクラスの宣言方法では、インスタンスから直接呼ばない関数はArrow関数式で記述します。なぜなら、既存の無名関数式ではインスタンスから直接呼ばなければ、thisの示す先がインスタンスではなくなってしまうからです。一方Arrow関数式は想定された挙動をする、つまり直接呼ばなくてもthisはインスタンスを示します。
82
82
 
83
83
  ```javascript
84
84
  class Test {

4

語法の修正

2019/08/31 21:36

投稿

frodo821
frodo821

スコア322

answer CHANGED
@@ -46,7 +46,7 @@
46
46
  追記
47
47
 
48
48
  コメントで、Arrow関数式に対する誤解がみられるので少し書いておきます。
49
- Arrow関数式は、定義された場所でのthisを___束縛します___。つまり、以下のコードは等価です:
49
+ Arrow関数式は、定義された場所でのthisを__束縛します__。つまり、以下のコードは等価です:
50
50
 
51
51
  ```javascript
52
52
  // これと
@@ -74,9 +74,9 @@
74
74
  (0, obj.func)() // ……4
75
75
  ```
76
76
  このコードで、1と2の戻り値は異なります。
77
- 1の戻り値は、論ずるまでもなく1です。一方、2の戻り値は5となります。なぜかというと、1と2でthisの示すものが異なるからです。これは、特定のオブジェクトobj.funcのthis束縛されていないことに由来します。
77
+ 1の戻り値は、論ずるまでもなく1です。一方、2の戻り値は5となります。なぜかというと、1と2でthisの示すものが異なるからです。これは、特定のオブジェクトobj.funcのthis束縛されていないことに由来します。
78
78
 
79
- 他方、3と4の戻り値は共に5となります。なぜなら、定義された場所のthis.xは5だからです。定義された場所とは、自分自身を格納しているオブジェクトの中を___意味しません___。そのオブジェクトが定義された場所こそがthisの指し示す先になります。
79
+ 他方、3と4の戻り値は共に5となります。なぜなら、定義された場所のthis.xは5だからです。定義された場所とは、自分自身を格納しているオブジェクトの中を__意味しません__。そのオブジェクトが定義された場所こそがthisの指し示す先になります。
80
80
 
81
81
  そこで、新しいクラスの宣言方法では、インスタンスから直接呼ばない関数はArrow関数式で記述します。なぜなら、既存の無名関数式ではインスタンスから直接呼ばなければ、thisの示す先がインスタンスではなくなってしまうからです。一方Arrow関数式は想定された挙動をする、つまり直接呼ばなくてもthisはインスタンスを示すからです。
82
82
 

3

アロー関数式について追記

2019/08/31 21:30

投稿

frodo821
frodo821

スコア322

answer CHANGED
@@ -40,4 +40,60 @@
40
40
  }
41
41
  </script>
42
42
  ```
43
- これで想定どおりの動作になるはずです。
43
+ これで想定どおりの動作になるはずです。
44
+
45
+ ----
46
+ 追記
47
+
48
+ コメントで、Arrow関数式に対する誤解がみられるので少し書いておきます。
49
+ Arrow関数式は、定義された場所でのthisを___束縛します___。つまり、以下のコードは等価です:
50
+
51
+ ```javascript
52
+ // これと
53
+ let obj = {
54
+ test: (function(){...}).bind(this);
55
+ };
56
+ // これはほぼ等しい
57
+ let obj = {
58
+ test: () => {...};
59
+ };
60
+ ```
61
+ 定義された場所のthisというのがまた難しい概念なのですが、以下のコード例を使って説明します。
62
+
63
+ ```javascript
64
+ var x = 5;
65
+ let obj = {
66
+ x: 1,
67
+ func() {return this.x},
68
+ func1: () => this.x
69
+ };
70
+ obj.func() // ……1
71
+ (0, obj.func)() // ……2
72
+
73
+ obj.func1() // ……3
74
+ (0, obj.func)() // ……4
75
+ ```
76
+ このコードで、1と2の戻り値は異なります。
77
+ 1の戻り値は、論ずるまでもなく1です。一方、2の戻り値は5となります。なぜかというと、1と2でthisの示すものが異なるからです。これは、特定のオブジェクトがobj.funcのthisに束縛されていないことに由来します。
78
+
79
+ 他方、3と4の戻り値は共に5となります。なぜなら、定義された場所のthis.xは5だからです。定義された場所とは、自分自身を格納しているオブジェクトの中を___意味しません___。そのオブジェクトが定義された場所こそがthisの指し示す先になります。
80
+
81
+ そこで、新しいクラスの宣言方法では、インスタンスから直接呼ばない関数はArrow関数式で記述します。なぜなら、既存の無名関数式ではインスタンスから直接呼ばなければ、thisの示す先がインスタンスではなくなってしまうからです。一方Arrow関数式は想定された挙動をする、つまり直接呼ばなくてもthisはインスタンスを示すからです。
82
+
83
+ ```javascript
84
+ class Test {
85
+ constructor(x) {
86
+ this.x = x;
87
+ }
88
+ func() {
89
+ return this.x;
90
+ }
91
+ func1 = () => this.x;
92
+ }
93
+
94
+ let ins = new Test(5);
95
+ ins.func() // -> 5
96
+ (0, ins.func)() // -> undefined
97
+ ins.func1() // -> 5
98
+ (0, ins.func1)() // -> 5
99
+ ```

2

文法の修正

2019/08/31 21:25

投稿

frodo821
frodo821

スコア322

answer CHANGED
@@ -8,7 +8,8 @@
8
8
  asyncFind(id) {
9
9
  return new Promise((res, rej) => setTimeout(() => {
10
10
  res(this.find(id))
11
- }, 1000)
11
+ }, 1000))
12
+ }
12
13
  }
13
14
  ```
14
15
 

1

編集途中で投稿してしまったため、編集を完了後再投稿

2019/08/31 21:01

投稿

frodo821
frodo821

スコア322

answer CHANGED
@@ -5,9 +5,38 @@
5
5
  find(id) { // 追記した関数
6
6
  return database.find(el => el.id === id)
7
7
  },
8
- async asyncFind(id) {
8
+ asyncFind(id) {
9
- return await new Promise(()setTimeout(() => {
9
+ return new Promise((res, rej) => setTimeout(() => {
10
- this.find(id)
10
+ res(this.find(id))
11
11
  }, 1000)
12
12
  }
13
- ```
13
+ ```
14
+
15
+ まずこのようにすることで、asyncFind関数がpromiseを返すようになります。値を受ける側は、このようにします:
16
+
17
+ ```vue
18
+ <script>
19
+ import products from 'products.js'
20
+ export default {
21
+ props: {
22
+ id: Number
23
+ },
24
+ data() {
25
+ return {
26
+ item: null
27
+ }
28
+ },
29
+ watch: {
30
+ id: {
31
+ handler() {
32
+ products
33
+ .asyncFind(this.id)
34
+ .then(it => this.items = it);
35
+ },
36
+ immediate: true
37
+ }
38
+ }
39
+ }
40
+ </script>
41
+ ```
42
+ これで想定どおりの動作になるはずです。