Intensive reading of big talk data structure, accompany you to win 45 points EP5 string application and implementation

Posted by Hayce on Sun, 03 Oct 2021 22:50:31 +0200

strlen function
Function of strlen

The strlen function calculates the length of a string

    char* p ="abcdef";
    int ret = strlen(p);
Action mechanism of strlen

When the string is stored, the last bit will be set to 0 by default

char* p = "abcdef";

abcdefABCDEF \ 0 is stored in memory
When our strlen function works, it starts from the address I passed in to the appearance of \ 0

Return value of strlen

Size when strlen returns value_ T is an unsigned integer
When an unsigned integer is subtracted from an unsigned integer, the result must be an unsigned integer, that is, a number greater than 0

if(strlen("abc")- strlen("abcdef")>0)
{
    printf("666");
}
else
{
    printf("777");
}

In this case, strlen"abc" returns 3, strlen ("abcdef") returns 7, which should be - 4 if understood by int type
However, the operation rules of unsigned numbers make it impossible for him to get a negative number, so - 4 is corrected to an integer and printed 666

Self realization of strlen
int myStrlen(char* p) //Cycle counter
{
    int sum=0;
    while(*(p++)!='\0')
    {
        sum++;
    }
    return sum;
}

int myStrlen2(char* p) //Pointer minus pointer writing
{
    char* p1 = p;
    while(*p!='\0')
    {
        p++;
    }
    return p - p1;
}

int myStrlen3( char* p) //Recursive implementation
{
    if(*p!='\0')
    	return 1 + myStrlen3(p++);
    return 0;
}
strcpy function
Functions of strcpy function

Copy a string into another string, put it from the beginning, and copy \ 0 into it
The strcpy function judges the string by \ 0, that is, I will not find it after I find \ 0
The target space must be large enough, or an error will be reported
The return value of the strcpy function is the address of the destination array

	char* p = "ab\0cde";
    char arr[] = "xxxxxxxxxxxxxxxx";

In the arr is ab \ 0xxxxxxxxxx

Simulation Implementation of strcpy function
char* myStrcpy(char* p1, char* p2)
{
    char* des = p1;
    while (*(p1++) = *(p2++))
    {
        ;
    }
}
return des;
strcat function
Functions of strcat function
char* strcat(char* dest, const char* src);

Concatenate the source function src after the destination string dest and return the first address of the destination space.
Note: the target string must have enough space
And both the source string and the destination string must have visible \ 0

Simulation Implementation of strcat function
char* mystrcat(char* dest, char* src)
{
    char* ret = dest;
    while(*dest!='\0')
    {
        dest++;
    }
    /*Found first string \ 0*/
    while(*dest++ = *src++)
    {
        ;
    }
    /*Complete connection*/
    return ret;	
}
strcnp
Functions of strcmp
int strcmp(char*p1, char*p2);

Compare the size of two strings. If p1 is less than p2, return a number less than 0
p1 greater than p2 returns a number greater than 0
p1 equals p2 and returns 0

Action principle of strcmp

Compare the first element of two strings. If it is different, end the comparison and return an integer
If the same, compare the next element and repeat the above process
Until the two elements are the same and both are \ 0, the judgment ends and returns 0

char* p1 ="abc\0adc";
char* p2="abc\0sdasdads";
printf("%d", strcmp(p1,p2));// 0

According to the above principle, the judgment ends when they are the same and both are 0, so the two strings are judged to be the same·

Simulation Implementation of strcmp
int strcmp(char*s1, char*s2)
{
    while(*s1 == *s2)
    {
        if(*s1=='\0')
        	return 0;
        	s1++;
        	s2++;
    }
    return *s1 - *s2;
}
strncpy
Functions of strncpy
char* strncpy(char* dest, char*src, int n)

Indicates that the first n elements of src are copied to dest, and \ 0 is filled in position n+1
If src is less than n bits, it will be filled with \ 0 by default
strcnpy effectively solves the problem of blind copy of srcnpy

Simulation Implementation of strnpy
char* strnpt(char* dest, char* src, int n)
{
	char* ret = dest;
	for(int i = 0; i < n; i++)
	{
		if (drc[i] == '\0')
		{
			dest[i] = src[i];
			return ret;
		}
			dest[i] = src[i];
	}
	dest[n] = '\0';
	return ret;
}
strncat
How strncat works
char* strncat(char* dest, char*src, int n)

The work of strncat is divided into two steps
1, find the \ 0 bit of dest string
2. Put the first n elements of src from bit \ 0
3. Add 0 at the position of n+1 after putting it in
Note that if the number of src elements is less than n, 0 will be added after all the elements are filled

Simulation Implementation of strncat
char* mystrncat(char* dest, char* src, int n)
{
	char* ret = dest;
	while (*dest)
	{
		dest++;
	}
	//Get the \ 0 bits of the destination string
	for (int i = 0; i < n; i++)
	{
		if (src[i] == '\0')
			break;
		*dest = src[i];
		dest++;
	}
	*dest = '\0';
	return ret;
}
strncmp
How strncmp works
int strncmp(char* s1, char* s2, int n);

The comparison starts from the first element. If it is the same, the second element will be compared. If it is different, the corresponding value will be returned. The size of the value is the same as strcmp.
Unlike strcmp, strncmp compares only n times.

Simulation Implementation of strcmp
int mystrncmp(char* s1, char* s2, int n)
{
	for(int i = 0; i < n; i++)
	{
		if (s1[i] != s2[i])
			return s1[i] - s2[i];
	}
	return 0;
}
strstr
How STR works
char* strstr(char* s1, char* s2);

The function is to find the location of the first occurrence of s2 in s1. If the address of the first occurrence of s2 is found, NULL is returned if it is not found

Simulation Implementation of STR -- sliding window mode

######What is a sliding window?
Sliding window is used to compare the quantitative relationship within a fixed length range, which is often combined with dynamic programming.

In this function, we want to find s2 from the string s1, and take s2 as the window. s1 is equivalent to the windowsill. We move the window back again and again. If it matches exactly, it means that we have found it.

code implementation
char* strstr(char* s1, char* s2) //Sliding window matching mechanism
{
	if (*s2 == '\0')
		return s1;
	char* cp = s1;//Pointer to control window
	char* p1 = NULL;
	char* p2 = s2;
	//p1 and p2 are two pointers for specific comparison
	while (*cp)
	{
		p1 = cp;
		while (*p1 == *p2 && p1 != NULL && p2 != NULL)
		{
			p1++;
			p2++;
		}//Determine whether the window contents match
		if (*p2=='\0')
			return cp;//Determine whether it matches to the end
		cp++;//If it is a match, move the window back one bit
		p2 = s2;
	}
	return NULL;
}
Simulation of STR -- kmp algorithm

The next chapter details

memcpy
How mencpy works
void* memcpy(void* dest, void* src, size_t count);

Copy the first count bytes in src memory area to desr
memcpy operates on direct memory, which is different from strcpy using \ 0 as the end point of copy, and directly using count as the end point of copy

Simulation Implementation of memcpy

Before the simulation implementation, we have a key problem to be confirmed, that is, whether we copy memory one byte by one or four bytes.
In fact, this problem is also very difficult to solve. If you copy with non-one bytes, there are always some situations that cannot be satisfied. Therefore, we adopt byte by byte copy

void* memcpy(void* dest, void* src, size_t count)
{
    void* ret = dest;
    while(count != 0)
    {
        *(char*)dest = *(char*)src
        dest = (char*)dest + 1;
        src = (char*) src + 1;
    } 
    return ret;
}
Disadvantages of memcpy

memcpy does not support overlapping copies, that is, it does not support me to copy a part of myself to myself.
Because when we look at his simulation implementation, memcpy is a fact calculus, that is, we do it directly on ourselves, and then continue.
So when we use memcpy, we only connect two different strings, not ourselves

memmove

Disadvantages of memcpy

Memmove is an upgrade of memcpy. Compared with the possible coverage problems of right to left copy of memcpy, memmove explores the upgrade before copying. The specific process is shown in the following figure

When we want to move the first 16 bytes of src to dest, if we copy memecpy from left to right, the following will happen

(copy the first two to dest, and then move both pointers back)

(copy the last two in the same way in sequence)

At this time, the problem is obvious. Because the fixed copy from left to right fails to copy the overlapping area, memmove upgrades it

memcpy upgrade

As we analyzed earlier, when src is less than dest (as shown in the figure below), we cannot copy from left to right, but from right to left.

When src is greater than dest (as shown in the figure below), how do we copy it?

At this time, we find that copying from left to right can perfectly realize it

This is how memmove works

If src is greater than dest, we copy from left to right; if src is less than dest, we copy from right to left;

Simulation Implementation of memmove

According to the working principle we analyzed earlier, we should first classify it, and then implement it.

void* mymemmove(void* dest, void* src, size_t count)
{
	void* ret = dest;
	if (dest < src)
	{
		while (count--)  /*Cycle count times*/
		{
			*(char*)dest = *(char*)src;
			/*The type of pointer determines the size of the space referenced by the reference operation. Here, we copy each byte, so we need to convert it to a char * pointer*/
			dest = (char*)dest + 1;
			/*Since the pointer of void * type does not accurately dereference the size of the type, we need to convert them into char * type first if we want to move 1 byte back*/
			src = (char*)src + 1;
		}
	}
	else
	{
		while (count--)
		{
			*((char*)dest + count) = *((char*)src + count);
			/*In c language, counting starts from 0, so for so many bytes from dest to dest+count, the address of the last byte is dest+count - 1; the address of the first byte is dest + 0;*/
		}
	}
	return ret;
}

Topics: C data structure