From d418b159788f3ee164d3b55780a8a0f5bbac04c3 Mon Sep 17 00:00:00 2001 From: Alikia2x Date: Wed, 10 Apr 2024 15:55:18 +0800 Subject: [PATCH] test: text-classification --- .../Text Classification-checkpoint.ipynb | 33 +++++++ backend/nlp/Text Classification.ipynb | 87 +++++++++++++++++++ package.json | 2 +- pnpm-lock.yaml | 86 +++++++++--------- 4 files changed, 164 insertions(+), 44 deletions(-) create mode 100644 backend/nlp/.ipynb_checkpoints/Text Classification-checkpoint.ipynb create mode 100644 backend/nlp/Text Classification.ipynb diff --git a/backend/nlp/.ipynb_checkpoints/Text Classification-checkpoint.ipynb b/backend/nlp/.ipynb_checkpoints/Text Classification-checkpoint.ipynb new file mode 100644 index 0000000..8bf44f5 --- /dev/null +++ b/backend/nlp/.ipynb_checkpoints/Text Classification-checkpoint.ipynb @@ -0,0 +1,33 @@ +{ + "cells": [ + { + "cell_type": "code", + "execution_count": null, + "id": "0fbcb787-a093-4c31-96a0-22f65a3ee25b", + "metadata": {}, + "outputs": [], + "source": [] + } + ], + "metadata": { + "kernelspec": { + "display_name": "Python 3 (ipykernel)", + "language": "python", + "name": "python3" + }, + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.12.2" + } + }, + "nbformat": 4, + "nbformat_minor": 5 +} diff --git a/backend/nlp/Text Classification.ipynb b/backend/nlp/Text Classification.ipynb new file mode 100644 index 0000000..9820743 --- /dev/null +++ b/backend/nlp/Text Classification.ipynb @@ -0,0 +1,87 @@ +{ + "cells": [ + { + "cell_type": "code", + "execution_count": 14, + "id": "0fbcb787-a093-4c31-96a0-22f65a3ee25b", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "\u001b[33mWARNING: Skipping /opt/homebrew/lib/python3.11/site-packages/packaging-24.0.dist-info due to invalid metadata entry 'name'\u001b[0m\u001b[33m\n", + "\u001b[0m\u001b[33mWARNING: Skipping /opt/homebrew/lib/python3.11/site-packages/packaging-24.0.dist-info due to invalid metadata entry 'name'\u001b[0m\u001b[33m\n", + "\u001b[0m\u001b[33mWARNING: Skipping /opt/homebrew/lib/python3.11/site-packages/numpy-1.26.4.dist-info due to invalid metadata entry 'name'\u001b[0m\u001b[33m\n", + "\u001b[0m\u001b[33mWARNING: Skipping /opt/homebrew/lib/python3.11/site-packages/certifi-2024.2.2.dist-info due to invalid metadata entry 'name'\u001b[0m\u001b[33m\n", + "\u001b[0mRequirement already satisfied: huggingface_hub in /opt/homebrew/lib/python3.11/site-packages (0.20.3)\n", + "Requirement already satisfied: filelock in /opt/homebrew/lib/python3.11/site-packages (from huggingface_hub) (3.13.1)\n", + "Requirement already satisfied: fsspec>=2023.5.0 in /opt/homebrew/lib/python3.11/site-packages (from huggingface_hub) (2023.10.0)\n", + "Requirement already satisfied: requests in /opt/homebrew/lib/python3.11/site-packages (from huggingface_hub) (2.31.0)\n", + "Requirement already satisfied: tqdm>=4.42.1 in /opt/homebrew/lib/python3.11/site-packages (from huggingface_hub) (4.66.2)\n", + "Requirement already satisfied: pyyaml>=5.1 in /opt/homebrew/lib/python3.11/site-packages (from huggingface_hub) (6.0.1)\n", + "Requirement already satisfied: typing-extensions>=3.7.4.3 in /opt/homebrew/lib/python3.11/site-packages (from huggingface_hub) (4.8.0)\n", + "Requirement already satisfied: packaging>=20.9 in /opt/homebrew/lib/python3.11/site-packages (from huggingface_hub) (23.2)\n", + "Requirement already satisfied: charset-normalizer<4,>=2 in /opt/homebrew/lib/python3.11/site-packages (from requests->huggingface_hub) (3.3.2)\n", + "Requirement already satisfied: idna<4,>=2.5 in /opt/homebrew/lib/python3.11/site-packages (from requests->huggingface_hub) (3.6)\n", + "Requirement already satisfied: urllib3<3,>=1.21.1 in /opt/homebrew/lib/python3.11/site-packages (from requests->huggingface_hub) (2.1.0)\n", + "Requirement already satisfied: certifi>=2017.4.17 in /opt/homebrew/lib/python3.11/site-packages (from requests->huggingface_hub) (2023.11.17)\n", + "\u001b[33mWARNING: Skipping /opt/homebrew/lib/python3.11/site-packages/packaging-24.0.dist-info due to invalid metadata entry 'name'\u001b[0m\u001b[33m\n", + "\u001b[0m\u001b[33mWARNING: Skipping /opt/homebrew/lib/python3.11/site-packages/numpy-1.26.4.dist-info due to invalid metadata entry 'name'\u001b[0m\u001b[33m\n", + "\u001b[0m\u001b[33mWARNING: Skipping /opt/homebrew/lib/python3.11/site-packages/certifi-2024.2.2.dist-info due to invalid metadata entry 'name'\u001b[0m\u001b[33m\n", + "\u001b[0m\u001b[33mWARNING: Skipping /opt/homebrew/lib/python3.11/site-packages/packaging-24.0.dist-info due to invalid metadata entry 'name'\u001b[0m\u001b[33m\n", + "\u001b[0m\u001b[33mWARNING: Skipping /opt/homebrew/lib/python3.11/site-packages/packaging-24.0.dist-info due to invalid metadata entry 'name'\u001b[0m\u001b[33m\n", + "\u001b[0m\u001b[33mWARNING: Skipping /opt/homebrew/lib/python3.11/site-packages/packaging-24.0.dist-info due to invalid metadata entry 'name'\u001b[0m\u001b[33m\n", + "\u001b[0m" + ] + } + ], + "source": [ + "!pip install huggingface_hub" + ] + }, + { + "cell_type": "code", + "execution_count": 1, + "id": "e82bbe25-4b14-4aca-8761-bad2a63fccd2", + "metadata": {}, + "outputs": [ + { + "ename": "ModuleNotFoundError", + "evalue": "No module named 'huggingface_hub'", + "output_type": "error", + "traceback": [ + "\u001b[0;31m---------------------------------------------------------------------------\u001b[0m", + "\u001b[0;31mModuleNotFoundError\u001b[0m Traceback (most recent call last)", + "Cell \u001b[0;32mIn[1], line 1\u001b[0m\n\u001b[0;32m----> 1\u001b[0m \u001b[38;5;28;01mfrom\u001b[39;00m \u001b[38;5;21;01mhuggingface_hub\u001b[39;00m \u001b[38;5;28;01mimport\u001b[39;00m notebook_login\n", + "\u001b[0;31mModuleNotFoundError\u001b[0m: No module named 'huggingface_hub'" + ] + } + ], + "source": [ + "from huggingface_hub import notebook_login" + ] + } + ], + "metadata": { + "kernelspec": { + "display_name": "Python 3 (ipykernel)", + "language": "python", + "name": "python3" + }, + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.12.2" + } + }, + "nbformat": 4, + "nbformat_minor": 5 +} diff --git a/package.json b/package.json index f6f02cc..45912b5 100644 --- a/package.json +++ b/package.json @@ -31,7 +31,7 @@ "@testing-library/jest-dom": "^6.4.2", "@testing-library/react": "^14.3.0", "@types/jest": "^29.5.12", - "@types/node": "^20.12.6", + "@types/node": "^20.12.7", "@types/punycode": "^2.1.4", "@types/react": "^18.2.75", "@types/react-dom": "^18.2.24", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index b691ee6..cd02837 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -43,7 +43,7 @@ dependencies: version: 2.2.2 ts-node: specifier: ^10.9.2 - version: 10.9.2(@types/node@20.12.6)(typescript@5.4.4) + version: 10.9.2(@types/node@20.12.7)(typescript@5.4.4) valid-url: specifier: ^1.0.9 version: 1.0.9 @@ -65,8 +65,8 @@ devDependencies: specifier: ^29.5.12 version: 29.5.12 '@types/node': - specifier: ^20.12.6 - version: 20.12.6 + specifier: ^20.12.7 + version: 20.12.7 '@types/punycode': specifier: ^2.1.4 version: 2.1.4 @@ -84,7 +84,7 @@ devDependencies: version: 10.4.19(postcss@8.4.38) jest: specifier: ^29.7.0 - version: 29.7.0(@types/node@20.12.6)(ts-node@10.9.2) + version: 29.7.0(@types/node@20.12.7)(ts-node@10.9.2) jest-environment-jsdom: specifier: ^29.7.0 version: 29.7.0 @@ -570,7 +570,7 @@ packages: engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} dependencies: '@jest/types': 29.6.3 - '@types/node': 20.12.6 + '@types/node': 20.12.7 chalk: 4.1.2 jest-message-util: 29.7.0 jest-util: 29.7.0 @@ -591,14 +591,14 @@ packages: '@jest/test-result': 29.7.0 '@jest/transform': 29.7.0 '@jest/types': 29.6.3 - '@types/node': 20.12.6 + '@types/node': 20.12.7 ansi-escapes: 4.3.2 chalk: 4.1.2 ci-info: 3.9.0 exit: 0.1.2 graceful-fs: 4.2.11 jest-changed-files: 29.7.0 - jest-config: 29.7.0(@types/node@20.12.6)(ts-node@10.9.2) + jest-config: 29.7.0(@types/node@20.12.7)(ts-node@10.9.2) jest-haste-map: 29.7.0 jest-message-util: 29.7.0 jest-regex-util: 29.6.3 @@ -626,7 +626,7 @@ packages: dependencies: '@jest/fake-timers': 29.7.0 '@jest/types': 29.6.3 - '@types/node': 20.12.6 + '@types/node': 20.12.7 jest-mock: 29.7.0 dev: true @@ -653,7 +653,7 @@ packages: dependencies: '@jest/types': 29.6.3 '@sinonjs/fake-timers': 10.3.0 - '@types/node': 20.12.6 + '@types/node': 20.12.7 jest-message-util: 29.7.0 jest-mock: 29.7.0 jest-util: 29.7.0 @@ -686,7 +686,7 @@ packages: '@jest/transform': 29.7.0 '@jest/types': 29.6.3 '@jridgewell/trace-mapping': 0.3.25 - '@types/node': 20.12.6 + '@types/node': 20.12.7 chalk: 4.1.2 collect-v8-coverage: 1.0.2 exit: 0.1.2 @@ -774,7 +774,7 @@ packages: '@jest/schemas': 29.6.3 '@types/istanbul-lib-coverage': 2.0.6 '@types/istanbul-reports': 3.0.4 - '@types/node': 20.12.6 + '@types/node': 20.12.7 '@types/yargs': 17.0.32 chalk: 4.1.2 dev: true @@ -3194,7 +3194,7 @@ packages: chalk: 3.0.0 css.escape: 1.5.1 dom-accessibility-api: 0.6.3 - jest: 29.7.0(@types/node@20.12.6)(ts-node@10.9.2) + jest: 29.7.0(@types/node@20.12.7)(ts-node@10.9.2) lodash: 4.17.21 redent: 3.0.0 dev: true @@ -3266,7 +3266,7 @@ packages: /@types/graceful-fs@4.1.9: resolution: {integrity: sha512-olP3sd1qOEe5dXTSaFvQG+02VdRXcdytWLAZsAq1PecU8uqQAhkrnbli7DagjtXKW/Bl7YJbUsa8MPcuc8LHEQ==} dependencies: - '@types/node': 20.12.6 + '@types/node': 20.12.7 dev: true /@types/istanbul-lib-coverage@2.0.6: @@ -3295,13 +3295,13 @@ packages: /@types/jsdom@20.0.1: resolution: {integrity: sha512-d0r18sZPmMQr1eG35u12FZfhIXNrnsPU/g5wvRKCUf/tOGilKKwYMYGqh33BNR6ba+2gkHw1EUiHoN3mn7E5IQ==} dependencies: - '@types/node': 20.12.6 + '@types/node': 20.12.7 '@types/tough-cookie': 4.0.5 parse5: 7.1.2 dev: true - /@types/node@20.12.6: - resolution: {integrity: sha512-3KurE8taB8GCvZBPngVbp0lk5CKi8M9f9k1rsADh0Evdz5SzJ+Q+Hx9uHoFGsLnLnd1xmkDQr2hVhlA0Mn0lKQ==} + /@types/node@20.12.7: + resolution: {integrity: sha512-wq0cICSkRLVaf3UGLMGItu/PtdY7oaXaI/RVU+xliKVOtRna3PRY57ZDfztpDL0n11vfymMUnXv8QwYCO7L1wg==} dependencies: undici-types: 5.26.5 @@ -3584,7 +3584,7 @@ packages: hasBin: true dependencies: caniuse-lite: 1.0.30001607 - electron-to-chromium: 1.4.730 + electron-to-chromium: 1.4.731 node-releases: 2.0.14 update-browserslist-db: 1.0.13(browserslist@4.23.0) @@ -3787,7 +3787,7 @@ packages: /convert-source-map@2.0.0: resolution: {integrity: sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==} - /create-jest@29.7.0(@types/node@20.12.6)(ts-node@10.9.2): + /create-jest@29.7.0(@types/node@20.12.7)(ts-node@10.9.2): resolution: {integrity: sha512-Adz2bdH0Vq3F53KEMJOoftQFutWCukm6J24wbPWRO4k1kMY7gS7ds/uoJkNuV8wDCtWWnuwGcJwpWcih+zEW1Q==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} hasBin: true @@ -3796,7 +3796,7 @@ packages: chalk: 4.1.2 exit: 0.1.2 graceful-fs: 4.2.11 - jest-config: 29.7.0(@types/node@20.12.6)(ts-node@10.9.2) + jest-config: 29.7.0(@types/node@20.12.7)(ts-node@10.9.2) jest-util: 29.7.0 prompts: 2.4.2 transitivePeerDependencies: @@ -3976,8 +3976,8 @@ packages: /eastasianwidth@0.2.0: resolution: {integrity: sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==} - /electron-to-chromium@1.4.730: - resolution: {integrity: sha512-oJRPo82XEqtQAobHpJIR3zW5YO3sSRRkPz2an4yxi1UvqhsGm54vR/wzTFV74a3soDOJ8CKW7ajOOX5ESzddwg==} + /electron-to-chromium@1.4.731: + resolution: {integrity: sha512-+TqVfZjpRz2V/5SPpmJxq9qK620SC5SqCnxQIOi7i/U08ZDcTpKbT7Xjj9FU5CbXTMUb4fywbIr8C7cGv4hcjw==} /emittery@0.13.1: resolution: {integrity: sha512-DeWwawk6r5yR9jFgnDKYt4sLS0LmHJJi3ZOnb5/JdbYwj3nW+FxQnHIjhBKz8YLC7oRNPVM9NQ47I3CVx34eqQ==} @@ -4684,7 +4684,7 @@ packages: '@jest/expect': 29.7.0 '@jest/test-result': 29.7.0 '@jest/types': 29.6.3 - '@types/node': 20.12.6 + '@types/node': 20.12.7 chalk: 4.1.2 co: 4.6.0 dedent: 1.5.1 @@ -4705,7 +4705,7 @@ packages: - supports-color dev: true - /jest-cli@29.7.0(@types/node@20.12.6)(ts-node@10.9.2): + /jest-cli@29.7.0(@types/node@20.12.7)(ts-node@10.9.2): resolution: {integrity: sha512-OVVobw2IubN/GSYsxETi+gOe7Ka59EFMR/twOU3Jb2GnKKeMGJB5SGUUrEz3SFVmJASUdZUzy83sLNNQ2gZslg==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} hasBin: true @@ -4719,10 +4719,10 @@ packages: '@jest/test-result': 29.7.0 '@jest/types': 29.6.3 chalk: 4.1.2 - create-jest: 29.7.0(@types/node@20.12.6)(ts-node@10.9.2) + create-jest: 29.7.0(@types/node@20.12.7)(ts-node@10.9.2) exit: 0.1.2 import-local: 3.1.0 - jest-config: 29.7.0(@types/node@20.12.6)(ts-node@10.9.2) + jest-config: 29.7.0(@types/node@20.12.7)(ts-node@10.9.2) jest-util: 29.7.0 jest-validate: 29.7.0 yargs: 17.7.2 @@ -4733,7 +4733,7 @@ packages: - ts-node dev: true - /jest-config@29.7.0(@types/node@20.12.6)(ts-node@10.9.2): + /jest-config@29.7.0(@types/node@20.12.7)(ts-node@10.9.2): resolution: {integrity: sha512-uXbpfeQ7R6TZBqI3/TxCU4q4ttk3u0PJeC+E0zbfSoSjq6bJ7buBPxzQPL0ifrkY4DNu4JUdk0ImlBUYi840eQ==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} peerDependencies: @@ -4748,7 +4748,7 @@ packages: '@babel/core': 7.24.4 '@jest/test-sequencer': 29.7.0 '@jest/types': 29.6.3 - '@types/node': 20.12.6 + '@types/node': 20.12.7 babel-jest: 29.7.0(@babel/core@7.24.4) chalk: 4.1.2 ci-info: 3.9.0 @@ -4768,7 +4768,7 @@ packages: pretty-format: 29.7.0 slash: 3.0.0 strip-json-comments: 3.1.1 - ts-node: 10.9.2(@types/node@20.12.6)(typescript@5.4.4) + ts-node: 10.9.2(@types/node@20.12.7)(typescript@5.4.4) transitivePeerDependencies: - babel-plugin-macros - supports-color @@ -4815,7 +4815,7 @@ packages: '@jest/fake-timers': 29.7.0 '@jest/types': 29.6.3 '@types/jsdom': 20.0.1 - '@types/node': 20.12.6 + '@types/node': 20.12.7 jest-mock: 29.7.0 jest-util: 29.7.0 jsdom: 20.0.3 @@ -4832,7 +4832,7 @@ packages: '@jest/environment': 29.7.0 '@jest/fake-timers': 29.7.0 '@jest/types': 29.6.3 - '@types/node': 20.12.6 + '@types/node': 20.12.7 jest-mock: 29.7.0 jest-util: 29.7.0 dev: true @@ -4848,7 +4848,7 @@ packages: dependencies: '@jest/types': 29.6.3 '@types/graceful-fs': 4.1.9 - '@types/node': 20.12.6 + '@types/node': 20.12.7 anymatch: 3.1.3 fb-watchman: 2.0.2 graceful-fs: 4.2.11 @@ -4899,7 +4899,7 @@ packages: engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} dependencies: '@jest/types': 29.6.3 - '@types/node': 20.12.6 + '@types/node': 20.12.7 jest-util: 29.7.0 dev: true @@ -4954,7 +4954,7 @@ packages: '@jest/test-result': 29.7.0 '@jest/transform': 29.7.0 '@jest/types': 29.6.3 - '@types/node': 20.12.6 + '@types/node': 20.12.7 chalk: 4.1.2 emittery: 0.13.1 graceful-fs: 4.2.11 @@ -4985,7 +4985,7 @@ packages: '@jest/test-result': 29.7.0 '@jest/transform': 29.7.0 '@jest/types': 29.6.3 - '@types/node': 20.12.6 + '@types/node': 20.12.7 chalk: 4.1.2 cjs-module-lexer: 1.2.3 collect-v8-coverage: 1.0.2 @@ -5037,7 +5037,7 @@ packages: engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} dependencies: '@jest/types': 29.6.3 - '@types/node': 20.12.6 + '@types/node': 20.12.7 chalk: 4.1.2 ci-info: 3.9.0 graceful-fs: 4.2.11 @@ -5062,7 +5062,7 @@ packages: dependencies: '@jest/test-result': 29.7.0 '@jest/types': 29.6.3 - '@types/node': 20.12.6 + '@types/node': 20.12.7 ansi-escapes: 4.3.2 chalk: 4.1.2 emittery: 0.13.1 @@ -5074,13 +5074,13 @@ packages: resolution: {integrity: sha512-eIz2msL/EzL9UFTFFx7jBTkeZfku0yUAyZZZmJ93H2TYEiroIx2PQjEXcwYtYl8zXCxb+PAmA2hLIt/6ZEkPHw==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} dependencies: - '@types/node': 20.12.6 + '@types/node': 20.12.7 jest-util: 29.7.0 merge-stream: 2.0.0 supports-color: 8.1.1 dev: true - /jest@29.7.0(@types/node@20.12.6)(ts-node@10.9.2): + /jest@29.7.0(@types/node@20.12.7)(ts-node@10.9.2): resolution: {integrity: sha512-NIy3oAFp9shda19hy4HK0HRTWKtPJmGdnvywu01nOqNC2vZg+Z+fvJDxpMQA88eb2I9EcafcdjYgsDthnYTvGw==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} hasBin: true @@ -5093,7 +5093,7 @@ packages: '@jest/core': 29.7.0(ts-node@10.9.2) '@jest/types': 29.6.3 import-local: 3.1.0 - jest-cli: 29.7.0(@types/node@20.12.6)(ts-node@10.9.2) + jest-cli: 29.7.0(@types/node@20.12.7)(ts-node@10.9.2) transitivePeerDependencies: - '@types/node' - babel-plugin-macros @@ -5611,7 +5611,7 @@ packages: dependencies: lilconfig: 3.1.1 postcss: 8.4.38 - ts-node: 10.9.2(@types/node@20.12.6)(typescript@5.4.4) + ts-node: 10.9.2(@types/node@20.12.7)(typescript@5.4.4) yaml: 2.4.1 /postcss-nested@6.0.1(postcss@8.4.38): @@ -6273,7 +6273,7 @@ packages: '@babel/core': 7.24.4 bs-logger: 0.2.6 fast-json-stable-stringify: 2.1.0 - jest: 29.7.0(@types/node@20.12.6)(ts-node@10.9.2) + jest: 29.7.0(@types/node@20.12.7)(ts-node@10.9.2) jest-util: 29.7.0 json5: 2.2.3 lodash.memoize: 4.1.2 @@ -6283,7 +6283,7 @@ packages: yargs-parser: 21.1.1 dev: true - /ts-node@10.9.2(@types/node@20.12.6)(typescript@5.4.4): + /ts-node@10.9.2(@types/node@20.12.7)(typescript@5.4.4): resolution: {integrity: sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ==} hasBin: true peerDependencies: @@ -6302,7 +6302,7 @@ packages: '@tsconfig/node12': 1.0.11 '@tsconfig/node14': 1.0.3 '@tsconfig/node16': 1.0.4 - '@types/node': 20.12.6 + '@types/node': 20.12.7 acorn: 8.11.3 acorn-walk: 8.3.2 arg: 4.1.3