출처 : http://ccami.tistory.com/13 폭파당할지도 몰라서 일단 긁어오기...

 

윈도우7에서 원격 데스크톱 설정하는 방법 입니다 !!


원격 데스크톱은 어디서든 인터넷만 된다면 

1) 어디서든 본인의 컴퓨터에 접속을 할 수 있다는 장점이 있습니다. 

2) 접속하는 컴퓨터의 성능에 상관없이 본인의 컴퓨터의 성능을 사용할 수 있습니다.



설정하는 과정은 

1. 접속할 컴퓨터에 대한 설정

2. 공유기를 사용할 시 공유기 설정

3. 외부에서 WOL(Wake On Lan)을 사용하여 컴퓨터를 키는 방법

4. 외부에서 컴퓨터를 끄는 방법

으로 진행할거구요.


여기는 Part 1. 접속할 컴퓨터에 대한 설정 입니다.


설정해 주기 전에, 다른 컴퓨터에서 본인의 컴퓨터로 들어오려면 본인 확인이 필요하겠죠?

ID와 비밀번호를 먼저 설정해 줄게요.


실행을 켭니다.

(단축키 : 윈도우키 + R)

.

.

control userpasswords2 라고 입력 후 확인

.

.

.

.

추가 클릭

.

.

.

.

ID생성

.

.

.

.

비밀번호 설정

.

.

.

.

권한 설정

.

.

마치면 본인이 설정한 ID가 목록에 있을거에요.

.

.

.

그리고 시스템으로 갑니다.

(단축키 : 윈도우키 + Pause Break)

.

.

원격 설정 클릭

.

.

.

.

사용자 선택

.

.

.

.

추가

.

.

.

.

아까 생성한 ID를 넣어주고 확인을 누르면 완료됩니다.


이 과정까지가 원격 데스크톱을 연결하기 위해 연결될 컴퓨터에서 설정해야할 부분 입니다.



여기까지 설정을 하면 

공유기를 사용할 경우 : 내부 네트워크 에서는 다른 컴퓨터에서 본인컴퓨터로 접속이 가능해요!

공유기를 사용하지 않을 경우 : 외부에서도 접속이 가능해요!





내부 네트워크에서 접속방법


먼저 본인 컴퓨터의 IP를 확인해야 합니다.

실행 - cmd 입력

(단축키 : 윈도우 + R)

.

.

명령어 ipconfig 입력

.
.

.

.

IP주소 라고 떠있는 것이 본인 컴퓨터의 IP에요.

(여기서는 192.168.1.13)

--------------------------------------------------------------------------------

192.168.x.x로 시작하면 공유기를 사용하고 있는 경우이고 가상IP를 사용하는 중 이구요,

이 외의 다른 숫자 (14.32.xxx.xxx) 이런식으로 되어 있으면 공유기가 없는 경우에요.


가상IP를 사용하는 경우에는 외부 IP와 연결을 해서 외부에서 접속할 수 있도록 공유기에서 설정을 해 줘야 하구요, 그것은 Part 2에서 설명하도록 하겠습니다^^

--------------------------------------------------------------------------------


이 주소를 기억하시고

다른 컴퓨터에 가서

시작-모든 프로그램-보조프로그램-원격데스크톱 연결

(접속할 컴퓨터에서는 윈도우가 xp이건 7이건 상관이 없어요)



여기에 아까 본인 컴퓨터의 IP주소를 입력하면

아까 설정한 ID와 비밀번호를 넣는 창이 나올거에요.

입력 후 연결하면 짠 ! 하고 본인 컴퓨터가 화면에 나올거에요.

이때 당연히, 접속할 컴퓨터는 켜져있어야 하구요!



외부 네트워크에서 접속하려면 그냥 본인 컴퓨터 IP만 알면 외부에서 접속이 가능해요. 이때도 물론 컴퓨터가 켜져 있어야 겠지요!?






다음은 Part 2. 공유기를 사용할 시 공유기 설정 입니다.

공유기는 IPTIME 공유기를 기준으로 설명 할거구요.

죄송하지만 다른 공유기는... 모르겠지만 비슷 할 거에요.

See you at next Part !



예전 모 회사 프로그래머가 신의 한수를 알려주겠다고 memcpy를 한번 짜보라고 하시더군요..

그래서 그냥 생각나는데요 조금 노멀하게...

 

void MyMemcpy(void *dest, void *src, size_t len){

char *dest8 = (char*)&dest;

char *src8 = (char*)&src;

 

while(--len){

*dest8++ = *src8++;

}

}

 

했는데, 이거 봐서 님의 경력은 얼마 안되네요 ㅋㅋ 하시더군요

ㅡ_ㅡ...

 

그래서 조금 고친것이

dest메모리 영역과 src메모리 영역이 겹치는지 확인하는 코드를 넣었습니다.

bool MyMemCpy(void *dest, void *src, size_t len)
{
    char *dest8 = (char*)dest;
    char *src8 = (char*)src;

    /////////////////////////////////
    //dest ■■■■■              //1.dest 메모리 영역안에 src가 있거나
    //        src □□□□□
    //            dest ■■■■■  //2.src 메모리 영역안에 dest가 있으면 안됨
    /////////////////////////////////

    if((dest8 <= src8 //1검사
       && src8 <= dest8+len)
    ||(src8 <= dest8 //2검사
       && dest8 <= src8+len))
    {
        return false;
    }

    while(len--){
        *dest8++ = *src8++;
    }

    return true;
}

 

뭐 여기까지 하면 그래도 안전하지 않냐라는 생각이 들었습니다만...

 

최근 boost 라이브러리(mpl 프로그래밍)쪽을 공부하면서 이런 방법이 나오더군요..

#include <typeinfo>
#include <algorithm>
#include <iterator>
#include <memory>

#include <boost/test/included/prg_exec_monitor.hpp>
#include <boost/timer.hpp>
#include <boost/type_traits.hpp>

 

//기존의 copy와 차별화를 위한 네임스페이스
namespace opt{
    namespace detail{
        //이건 직접 대입시켜서 복사하는 방식
        template<typename l1, typename l2, bool b>
        l2 copy_imp(l1 first, l1 last, l2 out, const boost::integral_constant<bool, b>&)
        {
           while(first != last){
                *out = *first;
                ++out;
                ++first;
            }
            return out;
        }

 

       //memcpy를 이용하는 방식
       template<typename T>
       T* copy_imp(const T *first, const T *last, const boost::true_type&)
       {
            memcpy(out, first, (last-first)*sizeof(T));
            return out+(last-first);
        }
    }

 

    //실제 copy명령어
    template <typename l1, typename l2>
    inline l2 copy(l1 first, l1 last, l2 out)
    {
          //복사하는것의 타입을 알아내서
          typedef typename std::iterator_traits<l1>::value_type value_type;

 

    //l1에대해서 "C& C::operator=(const C&);" 와 같은 정의가 없다면
    //trivial_assignment operator 를 가지게 됨. 

    //하지만 컴파일러 능력상 이걸 알아내는건 제각각임;;;
    return detail::copy_imp(first, last, out, boost::has_trivial_assign<value_type>());

    }

}

 

/////////////////////////////////////////////////////////////////////////////////////////////////////

// 이 밑은 위의 소스를 테스트 하는 소스

const int array_size = 1000;
int   i_array_[array_size] = {0,};
const int ci_array_[array_size] = {0,};
char  c_array_[array_size] = {0,};
const char cc_array_[array_size] = {0,};

int *i_array   = i_array_;
const int *ci_array  = ci_array_;
char *c_array   = c_array_;
const char *cc_array = cc_array_;

const int iter_count = 1000000;

 

using namespace std;

int cpp_main(int argc, char* argv[])
{
    boost::timer t;
    double result;
 
    cout << "Measuring times in micro-seconds per "<< array_size << " elements processed" << endl;
    cout << "Testing copy... " << endl;
    cout << "  [some standard liberay version may already perform this optimisation.]" << endl;
  
    //////////////////////////////////////////////////////////////////////////
    //cache load
    opt::copy(ci_array, ci_array + array_size, i_array);

    //time optimised verstion
    t.restart();
    for(int i=0; i< iter_count; ++i){
        opt::copy(ci_array, ci_array + array_size, i_array);
    }
    result = t.elapsed();
    cout << "opt::copy<const int*, int*> : " << result << endl;

 

    //////////////////////////////////////////////////////////////////////////
    //cache load;
    std::copy(ci_array, ci_array + array_size, i_array);

    //time standard version
    t.restart();
    for(int i=0; i< iter_count; ++i){
        std::copy(ci_array, ci_array + array_size, i_array);
    }
    result = t.elapsed();
    cout << "std::copy<const int*, int*> : " << result << endl;

  

    //////////////////////////////////////////////////////////////////////////
    //cache load
    opt::copy(cc_array, cc_array + array_size, c_array);

    //time optimised verstion
    t.restart();
    for(int i=0; i< iter_count; ++i){
        opt::copy(cc_array, cc_array + array_size, c_array);
     }
     result = t.elapsed();
     cout << "opt::copy<const char*, char*> : " << result << endl;

 

     //////////////////////////////////////////////////////////////////////////
     //cache load;
     std::copy(cc_array, cc_array + array_size, c_array);

     //time standard version
     t.restart();
     for(int i=0; i< iter_count; ++i){
         std::copy(cc_array, cc_array + array_size, c_array);
     }
     result = t.elapsed();
     cout << "std::copy<const char*, char*> : " << result << endl;

  

     return 0;
}

 

메타프로그래밍은 프로그램 소스를 프로그래밍 하는 개념인데...

위의 메모리 복사 예제 처럼 C++의 템플릿을 가지고, 컴파일러가 타입에 따라 가장 적절한 알고리즘을 선택 할 수 있게 하거나

미리 상수 같은걸 프로그램 실행 시점에서 결정하지 않고 컴파일 시점에서 결정하게 하여

더 빠른 프로그램 속도를 갖게 하는 비법? 꼼수? 학문? 인거 같습니다.

 

진정한 신의 한수... orz....

 

문제는 내가 아직 이걸 프로젝트에 써먹으면서 머리로 이해 + 손으로 익어야 하는데.......

이 개념 자체가 난해하고 어려워서 자료도 그다지 많이 없고

그나마 boost로 익히는 메타프로그래밍 이라는 책을 사서 봤지만....

 

미국 책 스타일... orz...

그냥 개념만 쫙 ~~~ 설명됬고... 제가 멍청해서 그런지 개념 잡기가 너무 난해 하네요..

영어로 표현하면 보는 내내 so what? 이라는 느낌밖에 안왔습니다. ㅠㅠ

 

어쨋든.. 요즘 boost 쪽... 꽤 유용하고 재미있는 프로그래밍 방법론이라 생각하네요..

 

#include <iostream>

using namespace std;

 

//간단한 텍스트 뒤집기
void recive(char s[])
{
    for(int i=0, j=strlen(s)-1; i<j; ++i, --j){
        char t = s[i];
        s[i] = s[j];
        s[j] = t;
    }
}

 

//안전한 메모리 복사

//차라리 memcpy_s 사용할것 이건 안에 어셈이라 더 빠름
bool MyMemCpy(void *dest, void *src, size_t len)
{
     char *des8 = (char*)dest;
     char *src8 = (char*)src;

     /////////////////////////////////
     //dest ■■■■■               //1.dest 메모리 영역안에 src가 있거나
     //      src □□□□□
     //            dest ■■■■■   //2.src 메모리 영역안에 dest가 있으면 안됨
     /////////////////////////////////
 
     if((des8 <= src8    //1검사
                && src8 <= dest8+len)
     ||(src8 <= des8    //2검사
                && des8 <= src8+len))
     {
            return false;
      }

   

      while(len--){
            *des8++ = *src8++;
      }

      return true;
}

 

//////////////////////////////////////////////

int main()
{
      char s[5] = {'a','b','c','d', '\0'};
      char d[5];

      for(int i=0; i<strlen(s); ++i){
          cout << s[i] << ',';
      }

     cout << endl;
 

     recive(s);

     for(int i=0; i<strlen(s); ++i){
         cout << s[i] << ',';
     }
     cout << endl;
 
     if(MyMemCpy(&s[3], &s[0], _countof(d))){
         for(int i=0; i<strlen(d); ++i){
            cout << d[i] << ',';
         }
     }
     return 0;
}

 

 

 

 

 

출처 : http://vsts2010.net/712

 

VC10에서 선보였던C++11의 기능 중 강력하면서 사용하기 쉽고, 자주 사용한 기능이 아마 'auto'이지 않을까 생각합니다. 예전에 강연을 할 때 auto와 관련된 예제를 보여드리면 많은 분들이 아주 좋아하시더군요(좀 놀라기도 하시더군요^^). 어떤 분들은 딴 건 제쳐두고 이것 때문이라도 VC10을 사용해야겠다는 분들이 있었습니다.

이번 VC11에서도'auto'와 같은 강력한 기능이 있습니다. 바로 'range base for' 입니다. 이것을 사용하면 반복문을 아주 쉽고, 강력하게 사용할 수 있습니다.

VC 특화 기능인 for each와 비슷하기 때문에 기존에 for each를 사용하고 있다면 이제는 range base for로 쉽게 바꾸어서 사용하면 됩니다.

예제를 통해 일반적인 for , VC for each,range base for문의 차이를 예제를 통해서 보겠습니다.

< 예제. 1 >

#include <iostream>

int main()

{

int NumberList[5] = { 1, 2, 3, 4, 5 };

std::cout<< "일반적인 for "<< std::endl;

for( int i = 0; i < 5; ++i )

{

std::cout<< i << std::endl;

}

std::cout<< "VC++ 특화의 for each" << std::endl;

for each( int i in NumberList )

{

std::cout<< i << std::endl;

}

std::cout<< "range base for " <<std::endl;

for( auto i : NumberList )

{

std::cout<< i << std::endl;

}

return 0;

}

< 실행 결과 >


<예제.1>을 보면 일반적인 for 문은

for( int i = 0; i < 5; ++i )

와 같이 시작과 종료 조건, 증가 값 이렇게 3개의 조건에 의해서 반복 됩니다.

그러나 range base for문은 VC만의 반복문인 for each와 비슷하게 데이터셋 변수와 이 데이터셋 요소의 타입을 선언하면 됩니다.

for( auto i : NumberList )

기존의 for 문에 비해서 또는 for each 보다도 간편해졌고, for each는 표준이 아닌 VC만의 기능인 것에 비해서 range base for C++ 표준 기능입니다.

range base for 문의 문법은 아래와 같습니다.

for ( for-range-declaration : expression ) statement

range base for 덕분에 반복문의 사용이 쉬워졌고, for 문을 사용할 때 종료 조건이 잘못되어 메모리 침범을 하는 위험도 피할 수 있게 되었습니다.

'C/C++언어' 카테고리의 다른 글

memcpy에 대한 고찰...  (0) 2012.11.27
간단한 텍스트 뒤집기, 메모리 복사 함수  (0) 2012.10.19
[ VC11-C++11 ] range base for - 1  (0) 2012.09.24
코드 최적화 팁  (0) 2012.09.10
CAtlMap 사용법 정리  (0) 2012.08.25
MSXML 파싱  (0) 2012.07.03

+ Recent posts