ameeeee
12/31/2019 - 4:40 AM

学習メモ:js

  • 波括弧で終わる場合は末尾に;は必要ない(if文や関数宣言など
  • 関数式の場合は波括弧で終わる場合に;が必要

'use strict';

厳密なエラーチェック、書いておくとエラーが発見しやすくなるので必ず書いておくようにする

<script>
  'use script';
  console.log('Hello world!');
</script

値の型を調べる

console.log(typeof 'hello');

文字列を整数値に変換

console.log(parseInt('5', 10) + 3);
// 10進数の整数値に変換

真偽値

  • false <- 0, null, undefined, '', false
  • true <- それ以外

テンプレートリテラル:文字列sに変数の値を埋め込む記法

console.log(`hello ${i}`);
// クォーテーションの代わりにバッククォートを使う

do while

let hp = -50;
do {
  console.log(`${hp} HP left!`);
  hp -= 15;
} while (hp > 0);
// do内の処理が一度は実行される

配列を操作する

const scores = [80, 90, 40, 70];
scores.push(60, 50); // 複数追加可能
scores.shift(); // ひとつずつしか削除できない

const scores = [80, 90, 40, 70];
scores.splice(1, 1, 40, 50);
// splice(変化が開始する位置, 削除する要素の数, 挿入する要素, 挿入する要素)

// unshift() ・・・先頭に要素を追加
// shift() ・・・先頭の要素を削除
// push() ・・・末尾に要素を追加
// pop() ・・・末尾の要素を削除
// sclice() ・・・途中の要素を削除、追加する

スプレッド構文

配列の中に別の配列の要素を展開

const otherScores = [10, 20];
const scores = [80, 90, 40, 70, ...otherScores];

function sum(a, b) {
  console.log(a + b);
}
sum(...otherScores);
// sum(10, 20); と同じ

分割代入

const scores = [80, 90, 40, 70];

const [a, b, c, d] = scores;
// 個々の要素を定数に割り当てる

const [a, b, ...others] = scores;
// レスト構文:分割代入と一緒に使うと、割り当てた以外の要素をここで指定した名前の配列に格納する

let x = 30;
let y = 70;
[x, y] = [y, x];
// xとyを入れ替える

filter:条件に合う要素を配列sから取り出す

const numbers = [1, 4, 7, 8, 10];
// 配列から偶数のみ取り出してevenNumbersに代入
const evenNumbers = numbers.filter((number) => {
  if (number % 2 === 0) {
    return true;
  } else {
    return false;
  }
});

// 短く:こちらの条件式がtrueだったらtrue、falseだったらfalseを返しているので、この条件式自体をreturnするようにする
const evenNumbers = numbers.filter(number => number % 2 === 0);

オブジェクトの操作

const point = {
  x: 100,
  y: 180,
};

// 再代入
point.x = 120;
// point['x'] = 120;

// 要素を追加
point.z = 90;

// 要素を削除
delete point.y;

// オブジェクトをスプレッド構文で展開
const otherProps = {
  r: 4;
  color: 'red';
};
const point = {
  x: 100,
  y: 180,
  ...otherProps,
};
// オブジェクトの中ではキーの順番は保持されない

// レスト構文を使って要素を取り出す(定数として扱いたい場合など
const {x, r, ...others} = point;

// オブジェクトの要素をすべて取り出す
const point = {
  x: 100,
  y: 180,
};
// *オブジェクトではforEach()が使えない
// 1.キーを配列で取得
const keys = Object.keys(point);
keys.forEach (key => {
  console.log(`Key: ${key} Value: ${point[key]}`);
  // ※keyは文字列で取得されているのでpoint.keyではなく[]を使う
});

// 注意すべき変数の挙動
let x = 1;
let y = x;
x[0] = 5;
// 結果: xは5、yは1

let x = [1, 2];
let y = x;
x[0] = 5;
// 結果:xは[5,2]、yも[5,2]

// スプレッド演算子:オブジェクトの値そのものを代入
let x = [1, 2];
let y = [...x];
x[0] = 5;
// 結果:xは[1,2]、yは[1,2]

文字列の操作

// substring:部分文字列を取得する
const str = 'hello';
console.log(str.substring(2, 4)); // 結果:ll
// substring(開始位置, 終了位置);

// join():配列の要素を文字列として結合する
const d = [2019, 11, 14];
console.log(d.join('/')); // 結果:2019/11/14

// split():文字列を区切り文字で分割して配列にする
const t = '17:08:24';
console.log((t.split(':')); // 結果:["17", "08", "24"]

const [hour, minute, second] = t.split(':');
console.log(hour); // 結果:17
console.log(minute); // 結果:08
console.log(second); // 結果:24

数値の操作

const scores = [10, 3, 9];
let sum = 0;
scores.forEach(score => {
  sum += score;
});
const avg = sum / scores.length;

// 小数点以下切り捨て
console.log(Math.floor(avg)); // 7

// 小数点以下切り上げ
console.log(Math.ceil(avg)); // 8

// 四捨五入
console.log(Math.round(avg)); // 7

// 指定した桁数になるように数値を丸める
console.log(Math.toFixed(3)); // 7.333

// 乱数生成
console.log(Math.random());
// ※0以上1未満のランダムな数値を生成

ランダムな整数値を作る

console.log(Math.random());

// 0, 1, 2
console.log(Math.floor(Math.random() * 3));
// console.log(Math.floor(Math.random() * (n + 1));

// min, ..., max
//console.log(Math.floor(Math.random() * (max + 1 - min)) + min));
// (max + 1 - min)でminからmaxまでの距離を出して、+ minで最小値を底上げするイメージ

日時に関する命令


// 現在の日時にアクセス
const d = new Date();

// d.getFullYear(); // 年:2019
// d.getMonth(); // 月:0-11 ※0が1月
// d.getDate(); // 日:1-31
// d.getDay(); // 曜日:0-6 ※日が0
// d.getHours(); // 時間:0-23
// d.getMinute(); // 分:0-59
// d.getSeconds(); // 秒:0-59
// d.getMilliseconds(); // ミリ秒:0-999 1ms = 1/1000 sec

console.log(`${d.getMonth() + 1}月 ${d.getDate()}日`); // 11月23日
// ※実行環境のタイムゾーンに依存している点に注意
// getTime()だとUTCと呼ばれる協定世界日時の1970年01月01日00時00分00病からの経過ミリ秒にアクセスできる

// 特定の日時を扱う
const d = new Date(2019, 10); // 2019/11/01 00:00:00

d.setHours(10, 20, 30); // あとから特定の日時をセット 2019/11/01 10:20:30
d.setDate(d.getDate() + 3); // 3日後を取得  2019/11/04

comfirm:確認ダイアログ

let answer = confirm('削除しますか');
if(answer) {
  console.log('削除しました');
} else {
  console.lgo('キャンセルしました');
}

setInterval():タイマー機能

function shouwTime() {
  console.log(new Date());
  i++;
  if(i < 2) {
    clearInterval(intervalID);
  }
}
const intervalId = setINterval(showTime, 1000);
// 関数に()をつけると意味が違ってくるので注意
// 定数に代入しておくとタイマーの識別子がintervalIdに入る

setTimeout():指定した時間のあとに1回だけ処理を実行する

let i = 0;
function showTime() {
  console.log(new Date());
  const timeoutId = setTimeout(showTime, 1000);
  i++;
  if (i > 2) {
    clearTimeout(imtoutId);
  }
};
showTime();
  • setInterval()とsetTimeout()の違いは処理の時間が重なるかどうか、setIntervalはインターバルに処理の時間が重なるのに対し、setTimeoutは処理が終わってからつぎのインターバルが始まる。
  • setIntervalで処理の時間>インターバルとなる場合、処理が重なることでシステムに負荷がかかるので注意

小文字を大文字に

const name = 'namae';
console.log(name.toUpperCase()); // NAMAE

try{}catch(){}:例外処理

const name = 5;
try {
  console.log(name.toUpperCase());
} catch (e) {
  console.log(e);
}
console.log('finished');
// 想定していないエラーが起きたときにも処理を継続させる

DOM操作

// idを取得
// document.getElementById('target')

// classを取得
// document.getElementsByClassName('box')

// htmlの要素名で取得
// document.getElementsByTagName('li')

// cssのセレクタ名で取得
// 最初にみつかったひとつの要素
// document.querySelector('form button')
// 見つかったすべての要素
// document.queryAll('ul.menu > li')

document.querySelectorAll('li:nth-child(odd)').forEach(li => {
  li.textContent = 'li!';  
})
// ここで帰ってくるオブジェクトは、NodeListと呼ばれるもので、配列と似たようなデータ構造になる。したがってループを使って処理をする。

// 親要素、子要素を指定する
const ul = document.querySelector('ul');
  // console.log(ul.parentNode); // body
  // console.log(ul.children); // li
  // console.log(ul.children[0]);
for (let i = 0; i < ul.children.length; i++) {
  console.log(ul.children[i].textContent);
}
// この場合、HTMLCollectionという形式で子要素が取得されている
// 配列と似ているが使えるメソッドが異なっており、forEachが使えないという点に注意

// 要素の属性を操作
const h1 = document.querySelector('h1');
  // console.log(h1.title);
  // h1.title = 'Changed!';
h1.style.color = 'gray';
h1.style.backgroundColor = 'pink';

// カスタムデータ属性
const h1 = document.querySelector('h1');
console.log(h1.dataset.appId);
h1.dataset.message = 'this is custom message!';

// クラス属性を上書き
const div = document.querySelector('div');
div.className = 'box border-pink';

// クラス属性を追加
div.classList.add('border-pink');

// クラス属性を削除
div.classList.remove('box');

// 特定のクラス属性の有無をチェック
div.classList.contains('border-pink'); // true/falseで返される

// 特定のクラス属性がなければ追加、あれば削除
div.classList.toggle('border-pink');
// if (div.classList.contains('border-pink')) {
//   div.classList.remove('border-pink');
// } else {
//   div.classList.add('border-pink');
// }

// 要素を生成
const h1 = document.createElement('h1');
h1.textContent = 'Title';
document.body.appendChild(h1); // 親要素の最後の子要素として追加

const p = document.createElement('p');
p.textContent = 'Hello, hello, hello...';
document.body.appendChild(p);

const h2 = document.createElement('h2');
h2.textContent = 'Sub Title';
document.body.insertBefore(h2, p); // 親要素の中の特定の要素の前に追加

要素のコピー

const copy = p.cloneNode(true);
// const copy = p.cloneNode(false);
// falseだと子要素や孫要素はコピーせず空の要素だけをコピーする
document.body.insertBefore(copy, h2);

要素の削除

document.body.removeChild(h2);

フォームの扱い

<input type="text" value="hello">
<textarea>hello hello</textarea>
const text = document.querySelector('input[type="text"]');
const textarea = document.querySelector('textarea');

// inputのテキストもtextareaもvalueで入力値取得
console.log(text.value);
console.log(textarea.value);

// テキストにフォーカス
text.focus();

// テキスト全選択
text.select();

// テキスト選択不可に
text.disabled = true;
<input type="checkbox" name="os" value="mac"> macOS
<input type="checkbox" name="os" value="win" checked> Windows

<input type="radio" name="color" value="red" checked> Red
<input type="radio" name="color" value="blue"> Blue

<select>
  <option>item 0</option>
  <option selected>item 1</option>
  <option>item 2</option>
</select>
// チェックボックス
console.log(document.querySelectorAll('input[type="checkbox"]')[0].checked);
console.log(document.querySelectorAll('input[type="checkbox"]')[1].checked);
document.querySelectorAll('input[type="checkbox"]')[0].checked = true;

// ラジオボタン
console.log(document.querySelectorAll('input[type="radio"]')[0].checked);
console.log(document.querySelectorAll('input[type="radio"]')[1].checked);
document.querySelectorAll('input[type="radio"]')[1].checked = true;

// セレクタ
console.log(document.querySelectorAll('select > option')[0].selected);
console.log(document.querySelectorAll('select > option')[1].selected);
console.log(document.querySelectorAll('select > option')[2].selected);
document.querySelectorAll('select > option')[2].selected = true;

イベントリスナー

<button>OK</button>
const button = document.querySelector('button');
button.addEventListener('dblclick', () => {
  console.log('clicked!');
});

イベントオブジェクト

// document上でのマウスの座標をリアルタイムで取得
const div = document.querySelector('div');
document.addEventListener('mousemove', e => {
  div.textContent = `${e.clientX}:${e.clientY}`;
});

preventDefault:要素の規定の動作をキャンセルするメソッド

<head>
<style>
  .hidden {
    display: none;
  }
</style>
</head>
<body>
  <p>Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. <span class="hidden">Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. Hello. </span><a href="">read more ...</a></p>
const a = document.querySelector('a');
const span = document.querySelector('span');

a.addEventListener('click', e => {
  e.preventDefault();
  // <a>の規定の動作、ページ遷移をキャンセルする
  a.classList.add('hidden');
  span.classList.remove('hidden');
});
// dotinstall:
// JavaScriptでおみくじを作ろう

 'use strict';
 const btn = document.getElementById('btn');

  btn.addEventListener('click', () => {
    const results = ['大吉', '中吉', '凶', '末吉'];
    // const n = Math.floor(Math.random() * results.length);
    // btn.textContent = results[n];
    btn.textContent = results[Math.floor(Math.random() * results.length)];

    // switch (n) {
    //   case 0:
    //     btn.textContent = '大吉';
    //     break;
    //   case 1:
    //     btn.textContent = '中吉';
    //     break;
    //   case 2:
    //     btn.textContent = '凶';
    //     break;
    // }
  });
  
  
// 確率を操作する場合
  'use strict';
{
  const btn = document.getElementById('btn');

  btn.addEventListener('click', () => {
    // const results = ['大吉', '中吉', '凶', '末吉'];
    // const results = ['大吉', '大吉', '大吉', '大吉', '凶'];
    // btn.textContent = results[Math.floor(Math.random() * results.length)];
    const n = Math.random();
    if (n < 0.05) {
      btn.textContent = '大吉'; // 5%
    } else if (n < 0.2) {
      btn.textContent = '中吉'; // 15%
    } else {
      btn.textContent = '凶'; // 80%
    }
  });
}