Strcpy 기능 구현 - 기능을 통한 "프로그램의 아름다움" 발견 | 지속적인 최적화, 최적화 및 재최적화~


머리말

C 언어로 된 Strcpy 라이브러리 기능 의 자체 구현을 통해 프로그램 최적화의 아름다움을 탐구하고 프로그램의 신비 !


1. Strcpy 라이브러리 기능이란 무엇입니까?

여기에 이미지 설명 삽입
Strcpy 라이브러리 함수의 기능: 문자열 복사를 실현

strcpy ( char * destination, const char * source );

구현 원리: strcpy 함수의 괄호 뒤에 복사할 문자열의 주소를 넣고 괄호 앞에 복사된 문자열의 대상을 넣습니다. 주소 전송 통해 문자열을 복사합니다 .

위의 간단한 이해를 통해 실제로 문자 하나씩 교환하여 문자열을 복사하는 것이 가능하다는 것을 알 수 있으며 이제 Strcpy 기능 을 구현하는 사용자 정의 기능을 구현할 수 있습니다.


둘째, Strcpy의 사용

#include <stdio.h>
#include <string.h>
int main()
{
    
    
	char arr1[20] = "xxxxxxxxxx";
	char arr2[] = "hello";
	
	strcpy(arr1,arr2); //1.目标空间的起始地址, 2.原空间的起始地址
	
	printf("%s\n", arr1);
	
	return 0;
}

이미지 설명을 추가하세요
여기에 인쇄된 것은 복사된 문자열입니다.

일부 학생들은 "arr1 배열의 나머지 x는 어떻습니까?"라고 물을 수 있습니다.

여기에서 관찰할 수 있습니다. Strcpy는 arr2의 "hello"를 arr1로 복사합니다
(그리고 첫 번째 요소 를 하나씩 덮어씁니다) .

Essence: arr1 의 처음 몇 개의 "x" 를 arr2"hello \0" 으로 덮는 것 입니다.

즉, 복사한 arr1을 인쇄 printf 는 "\0" 이전의 모든 문자를 인쇄합니다 ("\0" 은 문자열의 끝 식별자임) . 따라서 "\0" 으로 인쇄 하고 인쇄를 중지합니다 .

이것이 나머지 "x"가 인쇄되지 않는 이유입니다.

이 작은 에피소드를 풀고 나면 기본적으로 Strcpy가 어떻게 작동하는지 이해하고
우리 언어로 구현해 봅시다!


3. My_Strcpy의 구현


1.“전채”

먼저 My_Strcpy를 구현할 프로그램을 준비합니다.

#include <stdio.h>
#include <string.h>
int main()
{
    
    
	char arr1[20] = "xxxxxxxxxx";
	char arr2[] = "hello";
	
	My_Strcpy(arr1,arr2); //1.目标空间的起始地址, 2.原空间的起始地址
	
	printf("%s\n", arr1);
	
	return 0;
}

2. My_Strcpy 함수 구현


Ⅰ. "복제 프로세스" 최적화

여기 에서 "전채"를 무시하고 직접
사용자 정의 기능 섹션을 시작 하십시오.

void My_Strcpy(char* dest,char* src) //dest指针接收目标数组的首元素地址;
                                     //src指针接收要复制的数组首元素地址
{
    
    
  while(*src != '\0')
  {
    
    
	*dest = *src;
	dest++;
	src++;
  } //但是这样设置循环条件的话,是不会把'\0'也给复制的
	//所以得加多一条语句
	*dest = *src; //因为上面循环已经让地址到'\0'的地方
	              //只是循环条件为假,所以不执行
	              //所以可以承接上面++后的地址,执行一次,即可把'\0'也复制
}

그러나 '\0'을 루프에도 통합할 수 있는 방법이 있습니까?

당신도 그러한 생각을 가지고 있다면 "프로그램의 아름다움" - 최적화
를 시작하신 것을 축하 드립니다.

그럼 '최적화' 를 시작해 봅시다 ! !

"한 단계"를 수행하려면 먼저 루프의 조건을 통합하려고 시도할 수 있습니다.

void My_Strcpy(char* dest,char* src) 
{
    
    
  while(*src != '\0')
  {
    
    
	*dest++ = *src++; //跟之前意思一样
	                  //先复制,然后地址++,然后解引用 复制
  } 
	*dest++ = *src++; 
}

'한 번에 한 걸음' 시작하자

void My_strcpy(char* dest,char* src) 
{
    
    
  while(*dest++ = *src++)
  {
    
     
	;  //上面的条件,既可以先复制
  }   //当复制'\0'后,条件判断为假,又可以退出循环
}   //这样不就能做到“一步到位”、“一石二鸟”了吗!

이것을 보면
'프로그램'이 가져다주는 '깨달음'이 느껴지시나요? 더 많은 "멋진"
것들이 있습니다! !


Ⅱ. "기능 내부" 최적화

함수의 실행 가능성을 보장하기 위해 전달된 것이 null 포인터 인지 여부 판단
해야 합니다. 이것이 "최적화"두 번째 포인트 입니다 ~

판단 작업을 위해 "assert()"
를 사용할 수 있습니다.

그런 다음 이것을 사용하여 전달된 두 포인터가 함수 의 실행정확성
보장 하기 위해 null 포인터인지 여부를 결정할 수 있습니다.

void My_Strcpy(char*dest , const char*src)  
{
    
    
	//判断传过来的 是否为空指针
	assert( src != NULL);//断言----需要引头文件 <assert.h>
    // 如果 != 则 为真--则不会报错,
	//如果为假(即 指针为 空指针)--则会报错                                                             
	assert( dest != NULL);
	while (*dest++ = *src++)
	{
    
    
		;
	}
}

assert 추가 의 또 다른 이점은 그것이 널 포인터 인 경우 프로그램 이 오류 위치를 신속하게 제공 할 수도 있다는 것입니다(이것은 if 문 이 할 수 없는 것 입니다)

다음과 같이:

여기에 이미지 설명 삽입

누가 그런 프로그램을 사용하는 것에 대해 걱정하지 않겠습니까?


Ⅲ. "함수 매개변수" 최적화

이전 "Strcpy 라이브러리 함수란 무엇인가" 를 다시 살펴보면 My_Strcpy 함수Strcpy 라이브러리 함수 와 비교하여 " 다르다"
는 것을 찾는 것이 어렵지 않습니다 . 이는 아직 "최적화" 의 여지가 있음을 나타냅니다 !



여기에 이미지 설명 삽입
My_Strcpy 함수
형식 매개변수 부분과 비교하여 여기 에서 "형식 매개변수" 부분 이 수정해야 할 " const" 가 더 많다는 것을 찾는 것은 어렵지 않습니다 .

지금 이 순간부터 생각을 시작해야 한다 - ​​이걸 왜 할까
[PS: 이 부지런한 사고 의 습관을 들이 는 것이 프로그램의 훌륭한 기준~]

이렇게 하면 복사 프로세스 중에 보호된 "복사된 콘텐츠"가 복사 프로세스 중에 변경되지 않도록 할 수 있습니다.

[PS: "포인터에서 const 연산자의 적용"에 대해서는 당분간 이야기하지 않겠습니다! ]
이 글이 잘 쓰여지고 이해하기 쉽다고 생각
되시면 좋아요, 리포스트, 즐겨찾기 해주시면 됩니다!
저자는 이와 관련하여 가능한 한 빨리 관련 콘텐츠를 게시할 예정입니다! !

요점으로 돌아가기

* 앞에 'const' 를 붙이면
* 소스 ( My_Strcpy의 ' * src '에 해당 ) 즉, 역참조상수 속성을 가 집니다. 복사 과정에서 소스 값은 변경 되지 않습니다 . *

소스의 주소가 변경되는 경우, 즉 소스에 해당하는 내용이 변경되는 경우에만 해당 값이 변경됩니다.

이것은 다음과 같은 문제를 효과적으로 피할 수 있습니다

void My_Strcpy(char* dest,const char* src) ![在这里插入图片描述](https://img-blog.csdnimg.cn/66a1220bbfbe4150bb78364a367522ee.png#pic_center)

{
    
    
  while( *src++ = *dest++)
  {
    
     
	;   //复制的时候,放错位置的情况
  }   
}

위의 문제가 발생하면 프로그램이 자동으로 오류를 보고하여 프로그램을 보호합니다.
여기에 이미지 설명 삽입

여기에 이미지 설명 삽입
이때 *src 는 assign 과 동일한 상수 속성 을 가지므로 등호 왼쪽에 상수를 배치할 수 없습니다 .

src가 가리키는 내용을 dest가 가리키는 공간에 복사한다. 본질적
으로, dest가 가리키는 내용이 수정되기를 바라며, src가 가리키는 내용은 수정되지 않기를 바란다.

이것이 우리의 "최적화"의 또 다른 포인트입니다~


Ⅳ. "함수 반환형" 최적화

다시 Strcpy 라이브러리 함수들을 비교해보면 , Strcpy 라이브러리 함수 들의 반환 타입 이 실제로 char 임을
찾는 것은 어렵지 않습니다 . * 이것은 다시 "최적화" 되지 않습니다 ~~

여기에 이미지 설명 삽입

라이브러리 함수 Strcpy는 실제로 대상 공간시작 주소반환 합니다.

그런 다음 다음 "최적화" 를 수행할 수 있습니다.

#include <stdio.h>
#include <string.h>

char* My_Strcpy(char*dest , const char*src)  
{
    
    

	char * ret = dest; //先保存起始地址下来
	
	assert(*src != NULL)                                                           
	assert(*dest != NULL);
	while (*dest++ = *src++)
	{
    
    
		;
	}
	
	return ret; //内容改变了,但地址没变--也就依旧可以使用了

}

int main()
{
    
    
	char arr1[20] = "xxxxxxxxxx";
	char arr2[] = "hello";
	
	printf("%s\n", My_Strcpy(arr1,arr2)); //这里就可以 “链式访问”
	                            //即【函数的返回值 为 printf的参数】
	                        //这样就可以很快的查看 目标空间内容是什么
	return 0;
}

char * return type 을 사용하면 대상 공간 내용이 더 빠른 것을 볼 수 있습니다 ~~



넷째, My_Strcpy 함수를 완성합니다.

요약하자면, My_Strcpy 함수 의 최적화 에
성공 했고 , 최적화할 수 있는 모든 포인트가 최적화되었습니다 ~, Strcpy 함수를 성공적 으로 복사 했습니다 . !

그러나 이것은 "큰 마녀를 보는 것은 작은 일"일 뿐이며 학생들에게 " 벽돌 을 세우고 옥을 끌어들이는" 역할 을 합니다. 학생들 도이 !

프로그래밍의 세계는 넓고 , 탐험하고 발견 하고 갑자기 깨달음을 얻는 순간을 찾기
위해 더 많은 미지의 것들이 여러분을 기다리고 있습니다 ~



5. 지원해주셔서 감사합니다! ! !


[이 글이 도움이 되셨다면 좋아요와 응원 부탁드립니다~]
[더 좋은 아이디어가 있다면 아래 댓글도 함께 해주시고, 서로에게서 배우고, 발전해 나가세요! ]

추천

출처blog.csdn.net/qq_62817113/article/details/121890169