C Programlama

C dilinde Strcpy() nasıl kullanılır?

C dilinde Strcpy() nasıl kullanılır?
Bu yazımızda C programlama dilindeki strcpy() fonksiyonunu öğreneceğiz. strcpy() işlevi, C programlama dilinde dize kopyalama işlemini gerçekleştirmek için çok popüler bir standart kitaplık işlevidir. Standart işlemleri gerçekleştirmek için C programlama dilinde birkaç standart başlık dosyası vardır. "dize.h”, dize işlemlerini gerçekleştirmek için birkaç standart kitaplık işlevi sağlayan bu tür başlık dosyalarından biridir. "strcpy()" işlevi, "string" tarafından sağlanan kütüphane işlevlerinden biridir.h”.

Sözdizimi:

char* strcpy (char* hedef_konumu, const char* kaynak_dize);

strcpy()'yi anlamak:

strcpy() işlevinin tek amacı, bir dizeyi kaynaktan hedefe kopyalamaktır. Şimdi strcpy() fonksiyonunun yukarıdaki sözdizimine bakalım. strcpy() işlevi iki parametreyi kabul edebilir -

strcpy() işlevinin kaynak dizeyi değiştirememesi için kaynak burada bir sabittir. strcpy() işlevi, kaynak dizeden hedefe tüm karakterleri (dizenin sonundaki NULL karakteri dahil) kopyalar. Kaynaktan hedefe kopyalama işlemi tamamlandıktan sonra, strcpy() işlevi, hedefin adresini arayan işlevine geri döndürür.

Burada dikkat edilmesi gereken önemli nokta, strcpy() fonksiyonunun kaynak dizgiyi hedef dizgeye eklememesidir. Bunun yerine hedefin içeriğini kaynak dizenin içeriğiyle değiştirir.

Ayrıca, strcpy() işlevi, hedefin boyutunun kaynak dizeden daha fazla olduğundan emin olmak için herhangi bir kontrol yapmaz, tamamen programcının sorumluluğundadır.

Örnekler:

Şimdi strcpy() fonksiyonunu anlamak için birkaç örnek göreceğiz:

  1. strcpy() - Normal Çalışma (örnek1.c)
  2. strcpy() - Durum-1 (örnek2.c)
  3. strcpy() - Durum-2 (örnek3.c)
  4. strcpy() - Durum-3 (örnek4.c)
  5. strcpy() - Kullanıcı Tanımlı Sürüm (örnek5.c)
  6. strcpy() - Kullanıcı Tanımlı Sürüm Optimize Edildi (örnek6.c)

strcpy() - Normal Çalışma (örnek1.c):

Bu örnek program, C programlama dilinde strcpy() işlevini kullanarak normal bir dize kopyalama işleminin nasıl gerçekleştirileceğini gösterir. Lütfen hedef dizenin uzunluğunun kaynak dizenin uzunluğundan (boş karakter dahil uzunluk 18'dir) daha büyük olan 30 (char target_str[30]; ) olduğuna dikkat edin, böylece hedef, hedef dizedeki tüm karakterleri barındırabilir. kaynak dizesi.

#Dahil etmek
#Dahil etmek
int ana()

char source_str[] = "www.linux ipucu.com";
char target_str[30];
printf("strcpy() fonksiyonunu çağırmadan önce : \n\n");
printf("\tSource String = %s\n", source_str);
printf("\tDestination String = %s\n\n", target_str);
strcpy(hedef_str, kaynak_str);
printf("strcpy() fonksiyonunu çalıştırdıktan sonra : \n\n");
printf("\tSource String = %s\n", source_str);
printf("\tDestination String = %s\n\n", target_str);
0 döndür;

strcpy() - Durum-1 (örnek2.c):

Bu örnek programın amacı, hedef dizgenin uzunluğu kaynak dizgenin uzunluğundan daha az olduğunda ne olacağını açıkça açıklamaktır. Bu gibi durumlarda, hedef konum, kaynak dizedeki tüm karakterleri (NULL karakter dahil) barındırmak için yeterli boşluğa/bayta sahip olmayacaktır. Her zaman aklınızda bulundurmanız gereken iki şey:

  1. strcpy() işlevi, hedefin yeterli alana sahip olup olmadığını kontrol etmeyecek.
  2. Bu, gömülü yazılımda tehlikeli olabilir, çünkü strcpy() hedefin sınırlarının ötesindeki bellek alanını değiştirecektir.

Örnek programa bakalım. source_str'yi tanımladık ve onu “www olarak başlattık.linux ipucu.dizgenin sonundaki Null karakteri de dahil olmak üzere, bellekte 18 bayt alacak olan com”. Ardından, başka bir karakter dizisi i bildirdik.e. yalnızca 5 boyutunda hedef_str. Bu nedenle, hedef_str, kaynak dizeyi toplam 18 bayt boyutunda tutamaz.

Ama yine de kaynak dizgiyi hedef dizgeye kopyalamak için strcpy() işlevini çağırıyoruz. Aşağıdaki çıktıdan, strcpy() öğesinin hiç şikayet etmediğini görebiliriz. Bu durumda, strcpy() işlevi, karakteri kaynak dizeden (kaynak dizede NULL karakteri bulana kadar) hedef adrese (hedef sınırı aşsa bile) kopyalamaya başlayacaktır. Bu, strcpy() işlevinin hedef dizi için herhangi bir sınır denetimi yapmadığı anlamına gelir. Sonunda, strcpy() işlevi, hedef diziye atanmamış bellek adreslerinin üzerine yazacaktır. Bu nedenle strcpy() işlevi, farklı bir değişkene tahsis edilmiş olabilecek bellek konumlarının üzerine yazacaktır.

Bu örnekte, aşağıdaki çıktıdan strcpy() fonksiyonunun kaynak dizginin üzerine yazdığını görebiliriz. Programcılar bu tür davranışlara karşı her zaman dikkatli olmalıdır.

#Dahil etmek
#Dahil etmek
int ana()

char source_str[] = "www.linux ipucu.com";
char hedef_str[5];
printf("strcpy() fonksiyonunu çağırmadan önce : \n\n");
printf("\tSource String = %s\n", source_str);
printf("\tDestination String = %s\n\n", target_str);
strcpy(destination_str, source_str);
printf("strcpy() fonksiyonunu çalıştırdıktan sonra : \n\n");
printf("\tSource String = %s\n", source_str);
printf("\tDestination String = %s\n\n", target_str);
//printf("Kaynak Adresi = %u (0x%x)\n", &source_str[0], &source_str[0]);
//printf("Hedef Adres = %u (0x%x)\n", &destination_str[0], &destination_str[0]);
0 döndür;

strcpy() - Durum-2 (örnek3.c):

Bu program, hedef dize boyutunun kaynak dize boyutundan büyük olduğu ve hedef dizenin zaten bir değerle başlatıldığı durumu gösterir. Bu örnekte, şunu başlattık:

  • source_str için "www.linux ipucu.com” [boyut = 17+1 = 18]
  • target_str - "I_AM_A_DESTINATION_STRING" [boyut = 25+1 = 26]

strcpy() işlevi, kaynak dizedeki 17 karakterin tümünü ve NULL karakterini hedef dizeye kopyalayacaktır. Ancak, hedef dizideki kalan baytları (Byte 19 - 26, bir tabanlı) değiştirmez/değiştirmez. Hedef dizi üzerinde yineleme yapmak için for döngüsünü kullandık ve hedef dizide 19 ile 26 arasındaki baytların değişmediğini kanıtlamak için tüm diziyi yazdırdık. Bu yüzden son çıktıyı şu şekilde görüyoruz:

"www.linux ipucu.com_STRING”.

#Dahil etmek
#Dahil etmek
/* Bu program şu durumlarda durumu gösterir:
hedef dize boyutu > kaynak dize boyutu
ve kopyalamak için strcpy() işlevini yürütürüz
hedefe kaynak dizesi.
Not: Hedef dize boyutu her zaman
kaynak dizeden büyük veya ona eşit olmak.
*/
int ana()

char source_str[] = "www.linux ipucu.com";
char target_str[26] = "I_AM_A_DESTINATION_STRING";
printf("strcpy() fonksiyonunu çağırmadan önce : \n\n");
printf("\tSource String = %s\n", source_str);
printf("\tDestination String = %s\n\n", target_str);
strcpy(hedef_str, kaynak_str);
printf("strcpy() fonksiyonunu çalıştırdıktan sonra : \n\n");
printf("\tSource String = %s\n", source_str);
printf("\tDestination String = %s\n\n", target_str);
/* for döngüsü kullanarak hedef dizgeyi yazdır*/
printf("Hedef dizini char ile yazdır : \n\n");
printf("\tHedef Dize = ");
for(int i=0; ben<25;i++)

printf("%c", target_str[i]);

printf("\n\n");
0 döndür;

strcpy() - Durum-3 (örnek4.c):

Bu programı, hedef olarak değişmez bir dize ile asla strcpy() çağırmamamız gerektiğini göstermek için bir örnek olarak düşündük. Bu tanımsız davranışa neden olacak ve sonunda program çökecek.

#Dahil etmek
#Dahil etmek
int ana()

char source_str[] = "www.linux ipucu.com";
printf("strcpy() fonksiyonunu çağırmadan önce : \n\n");
printf("\tSource String = %s\n", source_str);
/* Hedef olarak dizge değişmezi ile asla strcpy() çağırma.
Program çökecek.
*/
strcpy("destination_str", kaynak_str);
printf("strcpy() fonksiyonunu çalıştırdıktan sonra : \n\n");
printf("\tSource String = %s\n", source_str);
0 döndür;

strcpy() - Kullanıcı Tanımlı Sürüm (örnek5.c):

Bu örnek programda, strcpy() fonksiyonunun kullanıcı tanımlı bir versiyonunun nasıl yazılacağını gösterdik.

#Dahil etmek
char * strcpy_user_defined(char *hedef, const karakter * kaynak);
/* strcpy() fonksiyonunun kullanıcı tanımlı versiyonu */
char * strcpy_user_defined(char *hedef, const karakter * kaynak)

char * hedef_backup = hedef;
while(*src != '\0') /* '\0' bulunana kadar yineleyin.*/

*hedef = *src; /* Kaynak karakteri hedefe kopyala */
kaynak++; /* Kaynak işaretçisini artır */
hedef++; /* Hedef işaretçiyi artır */

*hedef = '\0'; /* Hedefe açıkça '\0' ekleyin*/
dest_backup döndür;

int ana()

char source_str[] = "www.linux ipucu.com";
char target_str[30];
printf("Kullanıcı tanımlı string kopyalama fonksiyonunu çağırmadan önce : \n\n");
printf("\tSource String = %s\n", source_str);
printf("\tDestination String = %s\n\n", target_str);
/* Kullanıcı tanımlı string kopyalama fonksiyonunu çağırıyor */
strcpy_user_defined(destination_str, source_str);
printf("Kullanıcı tanımlı dizi kopyalama fonksiyonunu çalıştırdıktan sonra : \n\n");
printf("\tSource String = %s\n", source_str);
printf("\tDestination String = %s\n\n", target_str);
0 döndür;

strcpy() - Kullanıcı Tanımlı Sürüm Optimize Edildi (örnek6.c):

Şimdi, bu örnek programda, strcpy()'nin kullanıcı tanımlı sürümünü optimize edeceğiz.

#Dahil etmek
char * strcpy_user_defined(char *hedef, const karakter * kaynak);
/* Kullanıcı tanımlı strcpy() fonksiyonunun optimize edilmiş versiyonu */
char * strcpy_user_defined(char *hedef, const karakter * kaynak)

char * hedef_backup = hedef;
while(*hedef++ = *src++)
;
dest_backup döndür;

int ana()

char source_str[] = "www.linux ipucu.com";
char target_str[30];
printf("Kullanıcı tanımlı string kopyalama fonksiyonunu çağırmadan önce : \n\n");
printf("\tSource String = %s\n", source_str);
printf("\tDestination String = %s\n\n", target_str);
/* Kullanıcı tanımlı string kopyalama fonksiyonunu çağırıyor */
strcpy_user_defined(destination_str, source_str);
printf("Kullanıcı tanımlı dizi kopyalama fonksiyonunu çalıştırdıktan sonra : \n\n");
printf("\tSource String = %s\n", source_str);
printf("\tDestination String = %s\n\n", target_str);
0 döndür;

Sonuç:

strcpy() işlevi, C programlama dilinde dize kopyalama işlemini gerçekleştirmek için çok popüler ve kullanışlı bir kitaplık işlevidir. Bu, esas olarak dizeyi bir konumdan başka bir konuma kopyalamak için kullanılır. Ancak, strcpy() işlevinin hedef dizi için sınır denetimi yapmadığını ve bunun göz ardı edildiğinde ciddi bir yazılım hatasına yol açabileceğini tekrarlamak istiyoruz. Hedef dizinin NULL karakteri de dahil olmak üzere kaynak dizedeki tüm karakterleri tutacak yeterli alana sahip olduğundan emin olmak her zaman programcının sorumluluğundadır.

How to Change Mouse and Touchpad Settings Using Xinput in Linux
Most Linux distributions ship with “libinput” library by default to handle input events on a system. It can process input events on both Wayland and X...
Remap your mouse buttons differently for different software with X-Mouse Button Control
Maybe you need a tool that could make your mouse's control change with every application that you use. If this is the case, you can try out an applica...
Microsoft Sculpt Touch Wireless Mouse Review
I recently read about the Microsoft Sculpt Touch wireless mouse and decided to buy it. After using it for a while, I decided to share my experience wi...