C# 메모리 구조

C# 2008. 12. 9. 19:15
C# 메모리 구조 C샵

2008/05/28 08:51

복사 http://blog.naver.com/organiza/70031491336

C#은 메서드, 변수, 클래스 객체 등의 값을 저장하는 3개의 메모리 공간을 갖고 있다.

 

1. 메서드 영역(Method Area):

- 클래스의 메서드에 대한 바이트 코드, 클래스의 전역 변수 등을 할당하는 메모리 영역

 

2. 스택(Stack):

 - 메서드가 실행될 때 매개변수, 메서드 내에 선언된 지역변수, 임시 변수들이 스택 메모리 영역에 저장되며 메서드 실행이 종료되면 스택 메모리는 시스템에 반환함

 

3. Heap:

  - 객체를 사용할때 사용하는 중요한 메모리 공간

     힙 메모리는 new 연산자를 사용해 인스턴스를 생성하는 메모리 공간이다.

     힙에는 클래스, 배열, 문자열 등의 객체 인스턴스를 저장함

 

 

 메서드 영역
 메서드의 바이트 코드
 클래스 변수
 

 

 스택(Stack)
 매개변수
 지역변수
 메서드 실행이 종료되면 스택 메모리는 시스템에 반환함

 

 힙(Heap)
클래스 객체
배열 객체
문자열 객체

 

[출처] C# 메모리 구조|작성자 첫키스


Posted by Sting!

댓글을 달아 주세요

객체지향이란 1편


1. 객체지향의 장점.
객체지향이라는 개념은 무엇보다 알기쉽고,만들기 쉽다는것입니다.
즉 어떠한 컴퓨터 프로그램을 만들때,현실세계에서 생각하는 것과 동일한 사고방식으로의 접근이 가능해졌다는 것이죠. 
그래서 객체지향이라는 개념을 설명할때,  현실세계의  인용이 자연스럽게 나오는 것입니다. 
또한 만들기 쉽다는건 그만큼 유지보수하는데에도 많은 비용을 요구하지  않는다는점 입니다.

2. 객체지향의 중요한 개념 3가지
   1. 상속성 (inheritance)
      객체지향을 말할때 상속성은 가장 중요한 요소들 중 한가지입니다.  상속성은 미리 만들어진

      소스를 가지고 공유하며 재사용하고,  또한 특별한 부분에 대해서는 다시 재정의해서 사용하는

      걸 말합니다.  즉, 개발하는데 있어서, 많은 부분을 생략할 수 있다는 거죠.또한, 어느부분에

      오류가 있을때,  한부분의 수정만으로,  그 소스를 이용해 만든 모든 소스의 오류를 방지할

      수 있다는 장점을  또한 가지고 있습니다.
   2. 다형성(Polymophism)
      뒤에서 다시 머리 터지게 설명 드리겠지만 맛뵈기로 간단하게나마 말씀드리자면 상속을 받은

      것을 그대로 사용하지않고 입맛에  맞게 바꾸어줄수 있도록 하는것이 다형성입니다.  

      OVERRIDEN의 개념입니다.  OVERRIDEN은  재사용성으로 통하기도 하는데 그말이 맞는 거

      같습니다. 뒤에가면  OVERRIDEN 않쓰고는 SOURECE가 만들어 지지 않습니다. 특히 상속을

      받은 경우는 더 하지요. 


   3. 캡슐화(Encapsulation)
      캡슐화라고 하는것은 어떠한 데이타를 보호할 수 있다는 점입니다. 즉 어떠한 소스를 만들었을

      때, 그 소스의 데이타를 보호할 수 있고,  보호 할 수 있다고 하는건 그 소스를 사용하는 입장에

      서보면,  더욱더 안정된(또는 검증된) 소스를 사용한다는 것입니다. 같은 개념으로 data hiding

      이라고 하는데 대부분의 번역서에선 데이타 은닉화라고합니다. 말이 좀 이상하죠? 이게 문제

      입니다. 차라리 영어를 그대로 보는게 속편하죠(음.. 옆길로 셌군...)  
                
객체지향의 중요한 개념3가지에 대해서 간략하게 나마 정리를 했습니다.  벌써 눈치들을 채셨겠지

만 저놈들은 따로따로  때어 놓고는 생각할 수가  없습니다. 상속이 이루어져야 다형성을 써먹을수

가  있고 상속성을 쓰기위해서는 데이타가 믿을 만해야 하는데 그걸 만들어 주는것은 캡슐화 입니

다.  그리고 완벽한 캡슐화를 이루기 위해서는 상속성과  다형성이 뒷받침이 되어야 함은 말할 필요

도 없지요. 예를 보면서 좀더 자세하게 이야기 해보겠습니다.(사실 캡술화가 젤루 만만해여^^;)


                class Date
                {
                        int day;
                int monty;
                    int year;
                }


 지금 제가 아주 간단하게  Date라는 class를 만들어 보았는데, 이 클래스를 가만히 생각하게 되면

 이런 점이 있을 수가 있겠죠. 지금 date라는 클래스는 날짜를 저장하기 위해서 만든건데 일단 day

 라는 변수를 살펴보면 31보다 더 커다란 숫자가 저장되면 날짜를 잘못저장하게되는 거겠죠? 

  그러니깐

   Date d = new Date();


  하고 객체를 생성한 후 d.day = 40; 이라고 하게 되면 우리가 생각하는 개념상 잘못된 날짜가 만들

  어 지겠죠? 이럴때 이런 변수들(외부에서 임의로 조작되었을때 원하지 않는결과가 나오는것들

  또는 잘못된 결과가 나오는것들) 에대해서 외부로 부터 접근 제한을 시키는 것이 바로

  encapsulation이라고  생각하시면 됩니다. 그래서 이런 캡슐화를 어떻게 구현하게 되냐면..


        class Date
        {
                private int day;
                private int month;
                private int year;
        }


라고 만드는 것이지요. 여기서 private는 접근제한자라 불리는 것인데. Date라는 클래스 외부에서의

접근을 막는 것입니다.즉


        Date d = new Date;


한 후에 d.day = 40; 이라고 하면 에러가 나게 되는 것이죠.. 즉 외부로부터 어떠한 데이터를  보호

한다는 의미죠. 그런데 이렇게 보호만 한다고 해서 되는건 아니겠죠? 보호하는것까지는 좋은데

일단 만들어 놓은걸 사용하지 못하게 되는 것이니깐요. 그래서 이렇게 보호해놓은 데이타를 메소드

를 통해서 접근을 허락하는 것입니다.


        class Date
        {
                private int day;
                public void setDay(int targetDay)
                {
                        day = targetDay;
                }
        }


 제가 설명하기 쉽게 일단 변수를 하나로 줄였습니다.  자 그럼 설명을 계속하면 보시는 대로 day라

 는 변수를 외부에서 접근하지 못하게 private로 선언한 다음 setDay라는 메소드를 제공해 주는것이

 죠.그런데 위에 것만 보면 그전것과 크게 달라진 점이 없죠? 지금 나온 에제도 day라는 변수에 잘

 못된 값이 들어갈 수 있을테니깐요. 그래서 메소드를 제공하긴 하는데 그냥 제공만 하는 것이

 아니라.
 

       class Date
        {
                private int day;
                public void setDay(int targetDay)
                {
                        if(day==targetDay)
                        else
                        {
             // 이곳에는 잘못입력했으니깐 다시 입력하라는 식의 코딩이 들어가면 되겠죠.
                        }
                }
        }


이런식으로 만드는 겁니다. 그래서 다시 정리를 하자면 캡슐화라는것이 어려운 개념은 아닙니다.

일단 외부에서 조작이 되면 안되는 그런 변수에 대해서 private라고 선언한후 대신 메소드를 통해서

접근할 수 있도록 해주는 것이죠. 그리고 그 메소드에는 어떠한 검사부분이 들어가면 됩니다. 지금

넣으려는 값이 제대로 된것인지 아닌지를.  그래서 제대로 된것이라면 그냥 넣으면 되는 거구요. 제

대로가 아니라면 어떠한 처리부분이 들어가면 되겠죠?
  
1. Creating an Object


보통 자바에서 primitive data type(자바의 기본 데이타 타입을 선언하게 되면 실제적인 메모리에

할당되게 됩니다. 그렇지만 primitive data type이 아니라면(바로 reference type일 경우) 실제적인

메모리 공간에 할당되는게 아닙니다.  그런 레퍼런스 타입은 어떠한 주소값이 저장될 공간이 만들

어 지는 것이고, 실제로 다른곳에 실제적인 Object 가 저장이 되는것 이지요. 이런걸 보면 어느

정도 C에서 말하는 Pointer와 비슷합니다. 하지만 자바는 Pointer를 제공해 주지 않지요. 그져

reference라고 말하는것 뿐. 그리고 Pointer 연산은 안됩니다.(해도 되긴한데 엉망이 되어 버리죠)

그건 프로그램의 견고성  때문이지요. 뒤에서 자바의 특징을 말씀드릴때  다시한번 정리하겠지만

자바는 performance보다는 완벽한 객체지향을 목표로 만들어 졌으며 또한 서버에서 돌아가는 프로

그램 개발이 목적이였으므로 상당한 수준의 보안성과 안전성을 가지도록 만들어 졌습니다. Point를

써보신분들은 아시겠지만 이놈이 시스템을 아예 날려버리기도 하니까요 각설하고 객체를 만들때는

밑에서 처럼 new keyword를 사용 하시면 됩니다.

        1) MyClass m = new MyClass();
                Or
        2) MyClass m;
                m = new MyClass();

첫번째 예제는 선언과 동시에 Object를 하는 것이고, 두번째 예제는 선언과 Object생성을 나누어서

하게 되는것이죠.  두 예제의 다른점은 별반 없다고 생각하셔도 상관없습니다. 그리고 이렇게 만들

어진 Object에 접근을 하려면 dot 를 사용합니다. "variable dot  member"의 형식입니다. 예를 들면

m.day 라는 식이죠. 바로 m이 어떤 객체를 가리키는 reference이구요, day가 그 객체가 가지고 있

는 member variable이 되는 거죠. 그럼 실제로 한번 예제를 해보도록 하죠. MyDate라는 class를

만들어 보도록 하겠습니다.

        class MyDate
        {
                int day;
                int month;
                int year;
        }

이렇게 만든 다음 javac로 compile하시면 되겠지요.
그다음 사용을 하시려면 객체를 만들어야 겠지요. 그래서 MyDate를 사용하는 class도 만들어

보겠습니다.

        class TestMyDate
        {
                public static void main(String args[])
                {
                        MyDate m = new MyDate();
                        m.day = 3;
                        m.month = 4;
                        m.year = 2000;
                        System.out.println("나의 생일은 " + m.year + "년 " +  m.month + "월 " + m.day +"일 입니다.");
                }
        }

위의 TestMyDate를 실행시켜 보면 "나의 생일은 2000년 4월 3일 입니다." 라는 문장이 출력될 것입

니다. 소스를 설명드리면 3번째 줄에서 MyDate라는 class를 사용하기 위해 Object를 만들었습니

다. 그리고 4번째 줄에서 6번째 줄까지m.variable의 형식을 사용해 member variable에 값을 할당

하는 것이지요. 그리고 나서 7번째 줄에서 그런 값을 가져와서 출력하게 되는 것입니다. 이런

식으로 만들어진 Object의 값을 가져오고 할당할때는 referenceName.variable의 형식을 사용하면

되는 것입니다.


객체지향이란 2편


오늘은 객체지향 언어에서 사용하는 "is a" 관계에 대해 알아보도록 하죠. 일단 간단하게 말씀드리

면 상속관계 라고 할 수 있습니다. 상속관계에서의 상위계념은 하위개녀들을 포괄할 수 있는 내용

들이 들어갑니다. 예를 들어 포유류를 볼때 포유류는 젖먹이는 동물을 말합니다. 따라서 가장 상위

계념은 젖먹인다가 포함되는건 당연하겠죠. 포유류라는게 이런 동물들의 공통점을 뽑아 만든 개념

이니깐요. 즉 우리가 프로그래밍을 하다 보면 이런  관계를 가진 클래스들을 만들게 되는데.. 이런

관계에서 포유류를 상위클래스, 그리고 사슴, 사람 그리고 토끼  를 하위클래스로 보면 되는 것이

죠. 이럴때 우리는 이런 말을 사용합니다. 사슴은 포유류다. 또는 사람은 포유류다라는 말을. 즉 우

리가 다음과 같은 클래스를 만들게 되면

                                  Employee
                                     |  
                                     |  
                                  Manager

즉 코딩은 다음과 같겠죠.
        
        class Employee
        {
                String name;
                int salary;
                int ssn;
        }


        class Manager extends Employee
        {
                String managerGroup;
                // any coding...
        }
        
이럴때 객체지향언어에서는 Manager is a Employee 라는 말을 사용합니다.위의 예와 같은 식이

죠.따라서 이런 "is a"관계가 바로 상속관계라고 생각하시면 됩니다.위에서 설명드리지 않은 것중에

extends라는 것이 있죠.이것이 바로 상속을 할때 사용하는 keyword입니다.  상위에 있는 클래스

(Employee를 말하죠.)의 모든것을 하위에  있는 클래스(Manager) 가 물려 받는 것이죠. 즉

Employee에 있는 Class에 있는 name, salary, ssn같은 것들을 Manager또한 사용하기 때문에

Manager를 새로 처음부터  만드는 것이 아니라 Employee를 상속받고 자신만의 변수(man
agerGroup)를 선언해서 사용하는 겁니다.  물론 재사용별骸?관련이 있겠구요. 자바에서는 단일

상속만을 지원합니다. 즉 모든클래스의 상위클래스는 반드시 하나만이 존재할 수 있다는 것입니다.

물론 그 상위클래스위의 상위클래스는 존재할 수 있겠죠. 바로 위가 하나라는 말입니다...물론 아시

죠? 또한 어제 했던 생성자와  연계시켜서생성자는 상속되질 않습니다. 당연하겠죠. 왜냐하면,  생

성자라고 하는 것이 하는일이 멤버 변수의 초기화를  하게 되는건데 상속을 받아서 새로운 멤버를

선언하게 될텐데.  그런건 자신의 클래스 안에서 해야되는거겠죠?  또한 생성자를 만드는 법이

return type이 없고,class의 이름과 같아야 하기 때문에 상속받아봐야 자신의 클래스에서는 생성자

의 역활을 할 수가 없겠죠?



객체지향이란 3편

객체의 다형성

객체지향의 진주이자 마지막 관문이며 가장많이 사용되며 가장많은 질문과 회의를 낳게하는 다형

성에 대해 적으며 간략한 객체지향에 대한 글을 접을까 합니다

1. 다형성(polymopism)
    A. 정의
         Super class type의 Reference변수로 sub class type의 객체를 참조한다. 쉽죠? ^^; 예를

         봅시다.
        예)
                abstracte class Employee
                {
                        String name;
                        float bs;
                        double salary;
                        abstracte public void setSalary();
                   //이렇게 하면 반드시 밑에서 overriden해야한다.
                  /* abstracte 선언은 밑에서 객체로 생성하지 못하게할 내용을  나타낼때 사용한다.
            또한 abstracte클레스라고 해서 반드시 포함된 모든것이 다 abstracte가 되는건 아니다.
                        */
                }

                class SalesEmployee extends Employee
                {
                        public void setSalary()
                        {
                                salary = bs*1.5;
                        }
                        public void aa()
                        {
                                System.out.println("aa");
                        }
                }

                class RegularEmployee extends Employee
                {
                        public void setSalary()
                        {
                                salary = bs*1.3;
                        }

                        public void bb()
                        {
                                System.out.println("bb");
                        }
                }
일단은 예제 설명은 접어두고 예제의 내용은 기억하기 바란다.
자아 이제 심오한 이야기를 하겠다.
                SalesEmployee s[] = new Employee[2];


이문장이 실행되면 결과는? 맞춘분께는 아무것도 못드림다. 결과는 에러. 그렇다면 아랫걸보자.


                Employee e[] = new SalesEmployee[2];


이문장은 정상적으로 실행이된다. 왜? 소스코드를 보면 SalesEmployee가 기억장소에 저장되면은

name, bs, salary, setSalary(), 그리고 aa가 기억되어진다. 근데 위의 문장은 Employee type으
로 객체를 선언했다. 그러면 레퍼런스하는곳이 자신이 레퍼런스하고자 하는 숫자보다 작으므로
에러가 발생한다. 밑에 문장은 그런 이유로 가능한것이다.
기억하자. sub class type의 레퍼런스로 super class를 참조할 수 없다.
이제 다형성을 정의헤보자. 객체지향이 제사용성의 측면을 무쟈게 강조하고 있다는건 다 아실것
이다. 그럼 그런 연유에서 상속성이 나오게 된것도 알것이다. 그렇다면 변화를 주지 않고  사용
할 수 있는 것의 한계는 불보듯 뻔한것이다. 하나의 선언되어진 객체를 여러가지형태로 재정의
해서 사용할 수 있는 것이 다형성이다.

 *overriden


 재정의라고도 한다. 위의 소스를 보자 실제 메인부분에서(아직은 없지만) setSalary를 호출한다
면 무엇이 호출될까? 정답은 밑에서 정의한 것이 호출된다. 어떤 메쏘드를 호출할 때 상속이 이
루어졌다면 그 상속의 틀에있는 생성자들에 대하여 override검사라는것을 jvm이 한다.   그레서
 맨 나중에 재정의 된것을 사용하게 되는것이다. 왜? 상상을 해보라. 기껏 재정의 해놓은게 늘쌍
 부모클레스의 것만 사용된다면 허무하지 않겠는가? 위 소스를 완성해보자.

                abstracte class Employee
                {
                        String name;
                        float bs;
                        double salary;
                        abstracte public void setSalary();
                }

                class SalesEmployee extends Employee
                {
                        public void setSalary()
                        {
                                salary = bs*1.5;
                        }
                        public void aa()
                        {
                                System.out.println("aa");
                        }
                }

                class RegularEmployee extends Employee
                {
                        public void setSalary()
                        {
                                salary = bs*1.3;
                        }

                        public void bb()
                        {
                                System.out.println("bb");
                        }
                }

                public class PolyTest
                {
                        public static void main(String args[])
                        {
                                Employee e[] = new Employee[2];
                                e[0] = new SalesEmployee;
                                e[0].bs=1000000;
                                e[0].setSalary();
                                e[1] = new RegularEmployee;
                                e[1].bs=1000000;
                                e[1].setSalary();
                                
                                System.out.println(e[0].salary+":"+e[1].salary);
                        }
                }

결과는? 직접해보시기를....
그리고 객체지향에 대해 궁금하신분은 아래 싸이트를 가보시기 바란다.
 www.omtgroup.com


Posted by Sting!

댓글을 달아 주세요

프로그래밍 격언모음

1. "오늘까지"라는 말은 "내일 아침까지"라는 말이다.



2. 프로그램은 내가 원하는대로 움직이지 않는다. 타이핑대로 움직인다.



3. 요구 사양은 프로그램을 완성한 후에 추가된다.

기본 사양은 완성품을 고객이 보고 나서 결정된다.

상세 사양은 사용자가 프로그램을 사용해 본 이후에 결정된다.



4. 소프트웨어 설계에는 두 개의 방법이 있다.



하나는 결함이 있을 수 없을 정도로 단순하게 만드는 방법이다.

다른 하나는, 분명한 결함을 눈치채기 어려울 정도로 복잡하게 만드는 방법이다.



5. 코드는 개발 현장에서 사용하는 것이 아니라 납품처에서 사용하는 것이다.

디버그는 납기일까지 하는 것이 아니라, 납품된 이후에 하는 것이다.



6. 프로그래머를 죽이기 위해서는 칼이 필요없다. 프로그램의 요구조건을 3번만 바꾸면 된다.



7. 다른 사람을 믿으라. 그 사람이 해결해줄지도 모른다.

주의사항 - 먼저 자신을 의심해라.



8. 개발에 마지막은 없다. 출시만이 있을 뿐이다.



9. 클라이언트의 요구사항이 제 아무리 뒤늦게 추가되어도 납기일은 변하지 않는다.

이것을「납기 불변의 법칙」이라고 한다.



10. 우리의 고객들은 물과 기능추가를 공짜라고 생각하고 있다.



11. 주머니가 짠 고객일수록 잔소리가 많다.



12. 개발 스케줄은 산수를 무시하며 짜여진다. 영업과는 1+1=2를 이해하지 못하는 사람의 모임이다.



13. 한 명이 쓰러지면 모두가 쓰러진다.



14. 버그가 너무 심하다? 걱정마라. 어느 순간 그것은 기본 사양이 될 것이다.



15. 좋은 설계는 한 명의 천재보다 세 명의 범재를 요구한다.

나쁜 설계는 백명의 범재보다 한 명의 천재를 요구한다.



16. 고객에게 시스템 엔지니어는 부하이며, 프로그래머는 가축이다.

시스템 엔지니어에게 고객은 돈이다.

프로그래머에게 고객은 보이지 않는 악성 바이러스다.



17. 돈과 시간만 있으면, 그 어떤 시스템이라도 만들 수 있다고 생각하는가?

웃어라. 그 기회는 영원히 주어지지 않는다.



18. 품질은 사양 변경의 수와 규모에 의해, 얼마나 열화될지 결정된다.



19. 영업과는 공상이 실현된다고 생각하는 몽상가이다.

시스템 엔지니어는 넘을 수 없는 벽이 없다고 믿는 모험가이다.

프로그래머와는 몽상가와 모험가에 의해 칠흑의 바다에 내던져진 표류자이다.



20. 유능한 프로그래머가 프로그램 설계개념도를 받아들고 최초로 하는 일은, 프로그램의

목적을 이해하는 것이다. 그리고 그 다음으로 하는 일은, 지정된 방법과 시간 안에는

도저히 그 목적을 완수할 수 없다는 사실을 시스템 엔지니어에게 이해시키는 일이다.



21. 프로그램이란, 운과 감에 의해서 작성되는 기적이다.

운과 감이 없다면, 그 기간 내에 그러한 목표를 실현될 수 있을 리 없다.

따라서 사양 변경은 기적에 트집을 잡는 건방진 행위이며, 사양 추가는 기적이 두 번

일어날 것으로 믿는 무모한 행위이다.



22. 시스템 엔지니어는 지구력, 프로그래머는 순발력.



23. 정시에 퇴근하면, 일이 늘어난다.



24. 완벽한 프로그램은 완벽한 시간과 돈을 필요로 한다.

미국의 국가 예산을 무제한으로 사용하는 NASA마저도, 아직 시간과 돈이 부족하다고 한다.



25. 눈으로 훑어볼 틈이 있다면 움직여라. 뇌세포보다 CPU가 더 해석이 빠르다. 그리고, 그 사이,

쉴 수 있다.



26. 불편함을 버그라고 부를 것인가, 사양 상의 제한 사항이라고 부를 것인가는 남겨진 개발일자와

납기일에 의해 결정된다.



27. 정장 대신 캐쥬얼을 입고 출근하는 "캐쥬얼 데이"를 세간에서는 휴일이나 공휴일이라고 부르는

것 같다.



28. 프로그램은 머리로 기억하지 않는다. 몸으로 기억한다.



29. 내일 쉴 수 있다면 오늘 죽어도 괜찮다.



30. 고객은 거짓말을 한다.

영업은 꿈을 말한다.

시스템 엔지니어는 공상을 이야기한다.

프로그래머는 과묵해진다. (혼잣말은 많아진다)



31.「네, 할 수 있습니다」라고 말하기 전에 10초만 곰곰히 다시 생각해보라.



32. 프로그래머는 1분 생각하고 1일을 코딩에 소비한다.

1시간 생각하고 1시간 코딩하는 대신에 말이다.



33. 납품 이후의 디버그는 버그를 부른다.



34. 세 개의 디버그는 하나의 버그를 낳는다. 이것을 버그의 엔드리스 루프라고 한다.



35. 안 좋은 예감은 반드시 적중한다. 그러나 프로그래머는 그 안 좋은 예감에 반응하지

않는다. 그것은 시스템 엔지니어의 일이다.



36. 아수라장을 해결할 수 있는 방법은 오직, 고객이 돈을 지불하는 것 뿐이다.



37. 아마추어는 버그발견의 천재이다.



38. 아, 그건 마이크로소프트에서만 가능한 주문입니다.



39. 프로그래머가 불만이라고 생각하는 부분은 고객도 반드시 불만이라고 생각한다.



40. 건강하기 때문에, 건강을 해친다.



41. 그건, 당신이 말한 요구조건입니다만.



42. 아, 개발실의 창문은 안 열립니다. 그 이유는 옛날에 한 프로그래머가 그 창문에서···



43. 고객은 최악의 사태를 믿지 않으며, 그 사태에 대한 준비를 악질적인 비용청구라고 생각한다.

시스템 엔지니어는 최악의 사태를 대비하고 준비하려 한다.

프로그래머는 최악의 사태를 누구보다 잘 예상하지만, 무시한다.



44. 만약 다른 직업을 갖게 된다면, 정시퇴근을「도망」이라고 부르지 않는 직업이 좋을 것 같다.



45. 시스템 엔지니어가 프로그래머에게 말하는「상식」은 3시간마다 변한다.



46. 최소한 자기가 쓴 시방서는 읽어주세요.



47. 고객이 시스템 엔지니어에게 사랑받는 방법은, 시스템 개발에는 시간이 곧 돈이라는 사실을

깨닫고 빨리 최종요구조건을 확정하는 것이다.



SE가 고객에게 사랑받는 방법은, 프로그래머에게 미움받는 것이다.



48. 납기일이란, 작업현장이 우리 회사에서 고객의 회사로 바뀌는 날을 의미한다.



49. 가끔 일어나는 버그는 버그가 아니다. 스펙이다.



50. 개발비의 30%는 프로그램의 요구조건을 확정하는데 사용된다.

개발비의 30%는 프로그램의 요구조건을 변경하는데 사용된다.

개발비의 30%는 프로그램의 버그를 잡는데 사용된다.

개발비의 10%만이 프로그램의 개발에 사용된다.
Posted by Sting!

댓글을 달아 주세요

*폼 등에서 enter키로 인한 불필요한 동작 회피하기 : Netscape에서는 다르게 처리해야 함.
*textarea, button, submit, cancel 외의 부분에서 Enter키 입력하면 Tab으로 전환시켜줌.


<body onKeyDown="javascript:event.keyCode =(event.keyCode == 13) ? ('textarea:button:submit:cancel:'.match 13:9):event.keyCode">
Posted by Sting!

댓글을 달아 주세요

Sub ... End Sub, Function ... End Function  둘의 차이점

공통점
- 특정 부분의 작업을 수행한다.
- 계산이나 작업의 처리를 위해서 필요한 값을 넘겨받을 수 있다.

차이점
- Sub 는 작업을 처리하지만, 결과값을 리턴시키지는 않는다
- Sub 는 작업의 처리를 위해서 일정한 자료를 받거나 받지 않을 수 있다.
- Function 은 작업을 수행하고, 결과값을 리턴한다.
- Function 은 작업의 처리중에 필요한 자료를 함수에 전달해야 한다.
- Function 은 작업의 결과를 리턴하기 위해서는 함수와 같은 명칭의 변수명에 값을
  넣어서 되돌려 보내야 한다.

호출예
- Sub : <% Call Sub_name(값)%>
- Function : <% 변수명 = Finction_name (값)%>
Posted by Sting!

댓글을 달아 주세요