diff --git a/react/src/practice/_components/button.tsx b/react/src/practice/_components/button.tsx
new file mode 100644
index 0000000..fb13fe3
--- /dev/null
+++ b/react/src/practice/_components/button.tsx
@@ -0,0 +1,8 @@
+interface Props {
+ onClick: () => void;
+ children: React.ReactNode;
+}
+
+export const Button = ({ children, onClick }: Props) => {
+ return ;
+};
diff --git a/react/src/practice/practice_1/index.tsx b/react/src/practice/practice_1/index.tsx
index 1555ced..a0455be 100644
--- a/react/src/practice/practice_1/index.tsx
+++ b/react/src/practice/practice_1/index.tsx
@@ -2,5 +2,5 @@
// 以下のコードを完成させて、画面に「Hello, World!」と表示してください。
export const Practice1 = () => {
- return <>{/* コードをここに書いてください */}>;
+ return
Hello, World!
;
};
diff --git a/react/src/practice/practice_2/index.tsx b/react/src/practice/practice_2/index.tsx
index 20ac54c..dac86a2 100644
--- a/react/src/practice/practice_2/index.tsx
+++ b/react/src/practice/practice_2/index.tsx
@@ -3,5 +3,5 @@
export const Practice2 = () => {
const name = 'Hello, React!';
- return ;
+ return {name}
;
};
diff --git a/react/src/practice/practice_3/index.tsx b/react/src/practice/practice_3/index.tsx
index f816a5a..bd5ef31 100644
--- a/react/src/practice/practice_3/index.tsx
+++ b/react/src/practice/practice_3/index.tsx
@@ -2,6 +2,12 @@
// 以下のコードを完成させて、isLoggedInがtrueの場合「Welcome back!」、それ以外の場合「Please sign in.」と表示するようにしてください。
export const Practice3 = () => {
- let isLoggedIn: boolean;
- return <>>;
+ let isLoggedIn: boolean = true;
+ let result = "";
+ if (isLoggedIn) {
+ result = 'Welcome back!';
+ } else {
+ result = 'Please sign in.';
+ }
+ return {result}
;
};
diff --git a/react/src/practice/practice_4/index.tsx b/react/src/practice/practice_4/index.tsx
index bc8a057..2c8f40d 100644
--- a/react/src/practice/practice_4/index.tsx
+++ b/react/src/practice/practice_4/index.tsx
@@ -7,5 +7,11 @@ export const Practice4 = () => {
{ id: 2, name: 'Banana' },
{ id: 3, name: 'Cherry' },
];
- return {/* items配列を使ってリストを作成してください */}
;
+ return (
+
+ {items.map((item) => (
+ - {item.name}
+ ))}
+
+ );
};
diff --git a/react/src/practice/practice_5/index.tsx b/react/src/practice/practice_5/index.tsx
index 187e841..1258274 100644
--- a/react/src/practice/practice_5/index.tsx
+++ b/react/src/practice/practice_5/index.tsx
@@ -1,5 +1,8 @@
// 演習5:商品リストの作成
+import { Button } from '@/practice/_components/button';
+import { Counter } from '@/practice/practice_6';
+
// MUST要件
// 商品リストを表示する。(例:Apple, Banana, Cherry)
// 商品ごとに「詳細を見る」ボタンを表示する。
@@ -18,7 +21,20 @@ export const Practice5 = () => {
];
return (
- <>
- >
+
+ {products.map((product) => (
+ -
+ {product.name}
+
+
+
+ ))}
+
);
};
diff --git a/react/src/practice/practice_6/index.tsx b/react/src/practice/practice_6/index.tsx
index 441c05d..8f5874a 100644
--- a/react/src/practice/practice_6/index.tsx
+++ b/react/src/practice/practice_6/index.tsx
@@ -1,10 +1,29 @@
// 問題1: useStateを使ったカウンター
// 次の条件を満たすカウンターコンポーネントを作成してください:
+import { Button } from '@/practice/_components/button';
+import { useState } from 'react';
+
// 初期値を0に設定します。
// 「増加」「減少」「リセット」の3つのボタンを追加します。
// ボタンをクリックすると、それぞれの機能が正しく動作します。
-export const Practice6 = () => {
- return <>{/* コードをここに書いてください */}>;
-}
\ No newline at end of file
+// export const Practice6 = () => {
+export const Counter = () => {
+ const [count, setCount] = useState(0);
+
+ const increase = () => setCount(count + 1);
+ const decrease = () => setCount(count - 1);
+ const reset = () => setCount(0);
+
+ return (
+ <>
+
+
+
+
+
+ {count}
+ >
+ );
+};
diff --git a/react/src/practice/practice_7/index.tsx b/react/src/practice/practice_7/index.tsx
index 8cb4410..e700406 100644
--- a/react/src/practice/practice_7/index.tsx
+++ b/react/src/practice/practice_7/index.tsx
@@ -1,6 +1,8 @@
// 問題2: useEffectを使ったデータ取得
// 以下の条件を満たすデータ取得コンポーネントを作成してください:
+import { useEffect, useState } from 'react';
+
// コンポーネントがマウントされたときにfetchDataからデータを取得します。
// データ取得中は「Loading...」と表示します。
// データ取得後は、取得した内容をリスト形式で表示します。
@@ -23,5 +25,35 @@ const fetchData = () => {
};
export const Practice7 = () => {
- return <>{/* コードをここに書いてください */}>;
-}
+ const [data, setData] = useState([]);
+ const [loading, setLoading] = useState(true);
+
+ useEffect(() => {
+ const getData = async () => {
+ try {
+ const result = await fetchData();
+ setData(result);
+ } catch (error) {
+ console.error('Failed Data Fetch', error);
+ }
+
+ setLoading(false);
+ };
+
+ getData();
+ }, []);
+
+ return (
+
+ {loading ? (
+
Loading...
+ ) : (
+
+ {data?.map((item) => (
+ - {item.name}
+ ))}
+
+ )}
+
+ );
+};
diff --git a/react/src/root/index.tsx b/react/src/root/index.tsx
index 324b8e2..d99f310 100644
--- a/react/src/root/index.tsx
+++ b/react/src/root/index.tsx
@@ -3,6 +3,7 @@ import { Practice2 } from '@/practice/practice_2';
import { Practice3 } from '@/practice/practice_3';
import { Practice4 } from '@/practice/practice_4';
import { Practice5 } from '@/practice/practice_5';
+import { Practice7 } from '@/practice/practice_7';
export const Root = () => {
return (
@@ -12,6 +13,7 @@ export const Root = () => {
+
>
);
};
diff --git a/typescript/src/practice_1/index.ts b/typescript/src/practice_1/index.ts
index 8ec4499..3ae9064 100644
--- a/typescript/src/practice_1/index.ts
+++ b/typescript/src/practice_1/index.ts
@@ -1,11 +1,14 @@
// 演習1: 以下のコードに適切な型注釈を付けてください。
-let username = 'John'; // 型: ?
-let age = 30; // 型: ?
-let isAdmin = true; // 型: ?
+let hoge: "hoge";
+const huga = "huga";
-let scores = [100, 90, 80]; // 型: ?
+let username: string = 'John'; // 型: ?
+let age: number = 30; // 型: ?
+let isAdmin: boolean = true; // 型: ?
-let user = {
+let scores: number[] = [100, 90, 80]; // 型: ?
+
+let user: {id: number; name: string; isActive: boolean;} = {
id: 1,
name: 'John',
isActive: true,
diff --git a/typescript/src/practice_2/index.ts b/typescript/src/practice_2/index.ts
index a8ec633..747ecdc 100644
--- a/typescript/src/practice_2/index.ts
+++ b/typescript/src/practice_2/index.ts
@@ -1,10 +1,17 @@
// 演習2: 以下の関数に型を追加してください。
// 以下のコメントを外して問題を解く
-// function add(a, b) {
-// return a + b;
-// }
+function add(a: number, b: number): number {
+ return a + b;
+}
-// function formatId(id) {
+
+
+function formatId(id: string): string {
+ return `ID: ${id}`;
+}
+
+// これもいける
+// function formatId(id: number): string {
// return `ID: ${id}`;
-// }
+// }
\ No newline at end of file
diff --git a/typescript/src/practice_3/index.ts b/typescript/src/practice_3/index.ts
index 92f5558..01efcbf 100644
--- a/typescript/src/practice_3/index.ts
+++ b/typescript/src/practice_3/index.ts
@@ -4,14 +4,21 @@
// Todo の状態を表す Union 型を type を使って定義してください。
// 以下のコメントを外して問題を解く
-// type TodoStatus = ;
-// interface Todo {
-// }
+// 複雑指定できる
+type TodoStatus = { id: number; text: string; status: "todo" | "in-progress" | "done"; };
-// // 次の配列が型チェックを通過するようにしてください。
-// let todos: Todo[] = [
-// { id: 1, text: "Learn TypeScript", status: "todo" },
-// { id: 2, text: "Build a project", status: "in-progress" },
-// { id: 3, text: "Review code", status: "done" },
-// ];
+// interfaceはobjectに
+interface Todo {
+ id: number;
+ text: string;
+ status: "todo" | "in-progress" | "done";
+}
+
+// 次の配列が型チェックを通過するようにしてください。
+let todos: Todo[] = [
+ { id: 1, text: "Learn TypeScript", status: "todo" },
+ { id: 2, text: "Build a project", status: "in-progress" },
+ { id: 3, text: "Review code", status: "done" },
+ // { id: 4, text: "test", status: "hoge" }, // Union型でエラーする
+];
diff --git a/typescript/src/practice_4/index.ts b/typescript/src/practice_4/index.ts
index 64edb40..14e62e2 100644
--- a/typescript/src/practice_4/index.ts
+++ b/typescript/src/practice_4/index.ts
@@ -8,6 +8,19 @@ const input = document.querySelector('input');
// エラーを解消してください。
// 以下のコメントを外して問題を解く
-// button.onclick = () => {
-// console.log(`Input length: ${input.length}`);
-// };
+
+if (button instanceof HTMLButtonElement && input instanceof HTMLInputElement) {
+ button.onclick = () => {
+ console.log(`Input length: ${input.value.length}`);
+ };
+}
+
+// 解答例
+// const buttonAnswer = document.querySelector('button');
+// const inputAnswer = document.querySelector('input');
+
+// if (button && input) {
+// button.onclick = () => {
+// console.log(`Input length: ${input.value.length}`);
+// };
+// }
diff --git a/typescript/src/practice_5/index.ts b/typescript/src/practice_5/index.ts
index c7bdfa0..df0dc19 100644
--- a/typescript/src/practice_5/index.ts
+++ b/typescript/src/practice_5/index.ts
@@ -2,24 +2,20 @@
// 次の型を完成させてください。
// 問題1: 戻り値の型を取得する
-// 関数 T の戻り値の型を取得する型 `MyReturnType` を作成してください。
-
-// ヒント:
-// - 戻り値の型を取得するには、`infer` を使用して型を推論します。
-// - https://typescriptbook.jp/reference/type-reuse/infer
+type MyReturnType any> = T extends (...args: any) => infer R ? R : never;
// 使用例:
-// type Foo = () => number;
-// type Bar = () => string;
+type Foo = () => number;
+type Bar = () => string;
-// 問題2: オブジェクトの特定のキーを省略する型
-// オブジェクト T からキー K を省略する型 `OmitKey` を作成してください。
+type FooReturnType = MyReturnType; // number
+type BarReturnType = MyReturnType; // string
-// ヒント:
-// - `Exclude` ユーティリティ型を使用して、特定のキーを取り除きます。
-// - 構文: `Exclude`
-// - 残ったキーで新しいオブジェクト型を構築します。
+// 問題2: オブジェクトの特定のキーを省略する型
+type OmitKey = {
+ [P in Exclude]: T[P];
+};
// 使用例:
-// type User = { id: number; name: string; age: number };
-// type WithoutAge = OmitKey; // { id: number; name: string; }
+type User = { id: number; name: string; age: number };
+type WithoutAge = OmitKey; // { id: number; name: string; }