JavaScript - 내장함수, 객체, 생성자 함수, 캡슐화, 상속(호출), 기본자료형

|
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>0906 실습</title>
<script type="text/Javascript">

/*구구단 만들기 실습*/
function calculate(gugu){
	// $("#gugu").val(gugu); jquery 방식
	// var gugu = $("#gugu").val(); jquery 방식
	var gugu = document.getElementById('gugu').value; // 자바스크립트로 input 값 가져오기
	gugu = Number(gugu);
	if(isNaN(gugu) || gugu <=0 ){ // isNaN : number가 NaN(숫자가 아님)인지 확인.(숫자 체크)
		alert('숫자를 입력해주세요');
	} else {
			document.write("<table border=1>");
			document.write("<tr>" + "<td>" + "X" + "</td>");
				for(var j=1; j<=9; j++){ // * 9까지
					document.write("<td>" + j + "</td>");
				}
				for(var i=1; i<=gugu; i++){ // 몇단까지
					document.write("<tr>" + "<td>" + i + "</td>");
					for(var j=1; j<=9; j++){ // * 9까지
						document.write("<td>" + i*j + "</td>");
					}
					document.write("</tr>");
			}
			document.write("</table>");
		}
}

/*내장함수
//타이머함수
setTimeout(function(){
	alert('3초가 지났습니다. ㅇㅂㅇ');
}, 3000) // 3초후에 함수를 실행(3000은 milesecond)

//1초마다 함수를 실행
var intervalID = setInterval(function(){
	alert('<p>' + new Date() + '</p>');
}, 1000); // 1초마다 함수를 실행 // Fri Sep 06 2019 14:25:46 GMT+0900 (한국 표준시)

//5초 함수를 실행 후, 타이머를 종료 
setTimeout(function(){
	clearInterval(intervalID);
},5000);

//인코딩과 디코딩 함수
var URI = "http://hanb.co.kr?test=한글입니다.";

document.write(escape(URI)); // 적절한 정도로 인코딩
document.write(encodeURI(URI)); // 최소한의 문자만 인코딩
document.write(encodeURIComponent(URI)); // 대부분의 문자를 모두 인코딩


//코드실행함수
var willEval = '';
willEval += 'var number = 10;';
willEval += 'alert(number);';
eval(willEval); // String을 JavaScript코드로 실행 . 결과 10 alert 출력

//JavaScript 실행순서 A->C->B
//setTimeout은 script 블록이 모두 끝난 뒤에 호출
alert('A');
setTimeout(function(){
	alert('B');
}, 0);
alert('C');*/

//반복문과 콜백함수
//0,1,2 차례로 호출을 원하지만 3만 3번 호출됨
for(var i = 0; i < 3; i++){
	// (function (closed_i){ //클로저를 통해 0,1,2 가 호출되게 처리
		setTimeout(function (){
			alert(i); // alert(closed_i);
		},0);
	// })(i) //클로저를 통해 0,1,2 가 호출되게 처리
}

/*객체*/
//속성과 메소드
var person = {
		name: '홍길동',
		friend: '임꺽정',
		eat: function(food){
			alert(this.name + '이 ' + this.friend + '과 ' + food + '을 먹습니다.');
		}
};
person.eat('밥'); // 메소드 호출 : '홍길동이 임꺽정과 밥을 먹습니다.'
var output = '';
for(var item in person){ // 객체와 반복문
	output += item + ': ' + person[item] + '\n';
	// item은 name, friend, eat / person은 value
}

/*객체관련 키워드*/
// in 키워드 : 객체 내 속성존재여부 확인
output += "'name' in person: " + ('name' in person) + '\n'; // 결과 : true
// with 키워드 : 객체명 생략
with(person){
	output += 'name: ' + name + '\n'; // name: 홍길동
	output += 'friend: ' + friend + '\n'; // friend: 임꺽정
}

/*객체의 속성 추가와 제거*/
var stu = {};
stu.이름 = '피구'; // 속성 추가
stu.장래희망 = '날강두';
stu.toString = function(){ // 메소드 추가
	var answer = '';
	for(var key in this){
		if(key != 'toString'){ // toString 메소드는 출력하지 않게함.
			answer += key + '\t' + this[key] + '\n';
		}
	}
	alert(answer);
};
delete(stu.이름); // 속성제거. 배열에서의 delete는 undefined로 만드는 것.

//객체실습
var students = [];
students.push({ 이름 : '포그바', 국어: 99, 수학:88, 영어:77, 과학: 55});
students.push({ 이름 : '드록바', 국어: 89, 수학:78, 영어:67, 과학: 95});
students.push({ 이름 : '바밤바', 국어: 79, 수학:98, 영어:87, 과학: 15});
//모든 students 배열 내의 객체에 메소드를 추가합니다.
for(var i in students){
	//총점 구하는 메소드를 추가
	students[i].getSum = function(){
		return this.국어 + this.수학 + this.영어 + this.과학;
	}
	//평균을 구하는 메소드를 추가
	students[i].getAverage = function(){
		return this.getSum() / 4;
	};
}
//출력
var output = '이름\t총점\t평균\n';
for(var i in students){
	with(students[i]){
		output += 이름 + '\t' + getSum() + '\t' + getAverage() + '\n';
	}
}/*이름	총점	평균
포그바	319	79.75
드록바	329	82.25
바밤바	279	69.75*/

/*생성자 함수 : 자바의 class 와 같다. return 값이 없음. new를 통해서 생성가능. */
//객체실습 : 함수를 사용한 객체생성
function makeStudent(name, korean, math, english, science){
	var willReturn = {
			//속성
			이름 : name, 국어 : korean, 수학 : math, 영어 : english, 과학 : science,
			
			//메소드
			getSum: function(){
				return this.국어 + this.수학 + this.영어 + this.과학;
			},
			getAverage: function(){
				return this.getSum() / 4;
			},
			toString: function(){
				return this.이름 + '\t' + this.getSum() + '\t' + this.getAverage();
			}
	};
	return willReturn;
}

//1. 객체의 Property를 배열로 반환
function getPropertynames(o){
	var a = [];
	for(property in o) a.push(property); // 객체 o의 속성을 a 배열에 넣어라.
	return r;
}

// 2. from의 객체를 to로 Copy ( from의 프로퍼티를 to에 넣으면 됨.)
function copyProperties(from, to){
	if(!to) to = {};
	for(p in from) to[p] = from[p]; // from 에 있는 p를 반복해서 to 배열에 넣어라.
	return to;
}

// 3. From의객체를 to로 Copy하되 to에 없는 속성만 Copy 
function copyUndefineProperties(from, to){
	for(p in from){ // from에 있는 p를 반복
		if(!(p in to)) to[p] = from[p]; // to에 있는 p가 아닌 경우에만 -> from의 p를 to의 p에 넣어라.
	}
}

/*생성자함수
//생성자 함수 예제1
//Circle 클래스
function Circle(radius){ // 생성자 함수 정의
	this.r = radius;
}
//클래스 프로퍼티, 생성자함수의 프로퍼티
Circle.PI = 3.14159;
//인스턴스 메소드
Circle.prototype.area = function(){return Circle.PI * this.r * this.r;}
//클래스 메소드
Circle.max = function(a,b){
	if(a.r > b.r) return a;
	else return b; 
}
var c = new Circle(1.0); //인스턴스 생성
c.r = 2.2; //인스턴스 프로퍼티
var a = c.area(); // 인스턴스 메소드
var x = Math.exp(Circle.PI); // 클래스 프로퍼티
var d = new Circle(1.2); // 다른 인스턴스
var bigger = Circle.max(c, d); // 클래스 메소드

/*캡슐화*/
function Rectangle(w,h){// 변수를 선언
	var width = w;
	var height = h;
	//메소드선언
	this.getWidth = function(){return width;};
	this.getHeight = function(){return height;};
 // this.area = function(){return this.width * this.height;} // 생성자 함수에 메소드 속성 추가
	this.setWidth = function(w){
		if(w<0){
			throw '길이는 음수일 수 없습니다.';
		} else {
			width = w;
		}
	};
	this.setHeight = function(h){
		if(w<0){
			throw '길이는 음수일 수 없습니다.';
		} else {
			height = h;
		}
	}
}
Rectangle.prototype.getArea = function(){ // prototype에서 객체의 this에 접근가능
	return this.getWidth() * this.getHeight();
};
// var a = r.area(); //각 인스턴스들이 공유해야 하는 Property나 메소드를 정의(생성자 함수를 더 효율적으로 개선 :prototype사용)
var rectangle = new Rectangle(5, 7); //변수를 선언. property를 초기화하며 new와 함께 사용된다.
rectangle.setWidth(5); // 음수면 '길이는 음수일 수 없습니다.' 출력
alert('AREA : ' + rectangle.getArea()); // AREA : 35

/*상속 - JavaScript에서 정확한 상속방법은 없다.
instanceof 키워드로 특정 객체의 instance인지 확인 */ 
function Square(length){
	this.base = Rectangle; // 생성자로 Rectangle를 속성으로
	this.base(length, length); // 생성자 함수 Rectangle 호출
}
Square.prototype = Rectangle.prototype;
Square.prototype.constructor = Square; // 생략가능. constructor : 자신의 원소를 물어볼때 쓰임.
var square = new Square(5);
alert(square instanceof Rectangle); // 상속확인 : 결과값 true

/*상속예제
//모든 함수는 apply(), call() 메소드가 존재한다.
// 함수는 f()에 두 숫자를 전달하고 이 함수가 객체 o의 메소드 인 것처럼 호출할 경우
// 첫번째인자 : 함수가 소속되어 호출될 객체
// 나머지인자 : 함수의 전달인자
f.call(0, 1, 2);

//다음코드와 동일
o.m = f;
o.m(1,2);
delete o.m;

//apply()는 call()과 유사하지만 전달인자를 배열로 지정하는 것이 다름
f.apply(o, [1.2]);*/
//===============================
/*prototype(원형) : 상속의 구체적인 수단*/
// prototype에 저장된 속성들은 생성자를 통해서 객체가 만들어질 때 그 객체에 연결됨(prototype chain)
function MyParent(){
	this.property1 = "부모속성";
	console.log('Parent');
}
MyParent.prototype.info = function(){
	console.log('property1: ' + this.property1);
};
function MyChild(){
	this.property2 = "자식속성";
	console.log('Child');
}
MyChild.prototype = new MyParent(); //부모클래스 상속
MyChild.prototype.constructor = MyChild(); // 생성자 설정
MyChild.prototype.info = function(){ // 오버라이딩을 통한 기능확장 MyChild.prototype 은 MyParent를 가리킨다.
	MyParent.prototype.info.call(this); // 부모클래스의 info함수 호출
	console.log('info기능확장');
}
var child = new MyChild(); // 자식인스턴스 생성
child.info(); // 자식정보출력

/*기본자료형과 객체*/
// 기본자료형에 메소드 추가
var primitiveNumber = 273;
var objectNumber = new Number(273);
// Number 객체에 메소드를 추가하면 number dataType인 primitiveNumber도 추가된 메소드 사용가능
Number.prototype.method = function(){
	return 'Method on Prototype';
};
// 메소드 실행
var a1 = '';
a1 += primitiveNumber.method() + '\n';
a1 += objectNumber.method();

/*자료형 구분*/
//객체의 속성인 Constructor를 이용하면 같은 Type인지 비교하는 것이 명확함
var numberFromLiteral = 273;
var numberFromObject = new Number(273);
//자료형 확인
if(numberFromLiteral.constructor == Number){
	alert('numberFromLiteral은 숫자입니다.'); // 얼럿뜸
}
if(numberFromObject.constructor == Number){
	alert('numberFromObject는 숫자입니다.'); // 얼럿뜸
}

</script>
</head>
<body>

	몇단을 만들까요?<input type="text" id="gugu" name="gugu" >
	<input type="hidden" id="gugu" name="gugu" />
	<input type="button" id="make" name="make" value="구구단 만들기" onClick="calculate(gugu)"/>
	
</body>
</html>

'Bitcamp > BITCAMP - Front Web' 카테고리의 다른 글

JavaScript - LinkedList, nodeType(재귀), Event 핸들러, DOM  (0) 2019.09.10
JavaScript - Object 객체, DOM  (0) 2019.09.09
JavaScript - 클로저, Scope  (0) 2019.09.05
6일차 실습  (0) 2019.09.04
JavaScript - 자료형  (0) 2019.09.03
And