İki teli takas etmek için temperlenmiş fonksiyonlar kullanmaya çalışmak


9
#include<iostream>
#include<string>

template <typename T>
void swap(T a , T b)
{
  T temp = a;
  a = b;
  b = temp;
}

template <typename T1>
void swap1(T1 a , T1 b)
{
  T1 temp = a;
  a = b;
  b = temp;
}

int main()
{
  int a = 10 , b = 20;
  std::string first = "hi" , last = "Bye";

  swap(a,b);
  swap(first, last);   

  std::cout<<"a = "<<a<<" b = "<<b<<std::endl;
  std::cout<<"first = "<<first<<" last = "<<last<<std::endl;    

  int c = 50 , d = 100;
  std::string name = "abc" , surname = "def";

  swap1(c,d);
  swap1(name,surname);

  std::cout<<"c = "<<c<<" d = "<<d<<std::endl;
  std::cout<<"name = "<<name<<" surname = "<<surname<<std::endl;    

  swap(c,d);
  swap(name,surname);

  std::cout<<"c = "<<c<<" d = "<<d<<std::endl;
  std::cout<<"name = "<<name<<" surname = "<<surname<<std::endl;    

  return 0;
}

**Output**
a = 10 b = 20
first = Bye last = hi
c = 50 d = 100
name = abc surname = def
c = 50 d = 100
name = def surname = abc

Her ikisi de swap()ve swap1()temel olarak aynı işlev tanımlarına sahiptir, o zaman neden sadece swap()dizeleri değiştirir, swap1()olmasın?

Ayrıca stl dizelerinin varsayılan olarak argüman olarak nasıl aktarıldığını, yani değere veya referansa göre geçtiğini söyleyebilir misiniz?


4
Std :: swap ile ilgili sorun nedir ?
Jesper Juhl

1
Bunda yanlış bir şey yok. Temperlenmiş fonksiyonları öğreniyordum. Bu yüzden sadece pratik yapmak için bu kodu yazdım ama çıktı beni şaşırttı.
gettingBetterprogrammer

Yanıtlar:


9

İnsanların neden şimdi ADL'ye kaşlarını çattığını görebiliyorum ...

Gördüğünüz şey, Argümana Bağımlı Arama'nın bir etkisidir . swapUygulamanızın içine bir baskı eklerseniz , bunun için değilstd::string , yalnızca için çağrıldığını fark edersiniz int.

std::swapsürümünüz için tercih edilir, çünkü tür için açık bir uzmanlık vardır std::basic_string. Eğer olmasaydı, çağrı muhtemelen belirsiz olurdu.
Çünkü int, ad alanı stdarama sürecinde dikkate alınmaz, bu nedenle sürümünüz yalnızca kabul edilebilir.

Ayrıca bana stl dizelerinin varsayılan olarak argümanlar olarak nasıl aktarıldığını, yani değere veya referansa göre geçtiğini söyleyebilir misiniz?

Açıkça referans olarak işaretlemediğiniz sürece, C ++ 'da her şey değere göre iletilir.


bu kodu buradan kontrol edin: pastebin.com/E257yw04 . İşlevim swap1 (), dizeler için çağrılır, ancak yalnızca bir kez. Neden?
18:18

@dumb_programmer Kodunuzda iki swap1 çağrınız var (biri için intve biri için std::string) ve böylece iki çağrı yazdırılır. İki yapılan çağrılar var swapolan std::stringve bu kullanım std::swap(hiçbir yazdırma).
Yksisarvinen

Anladım!! Çok teşekkür ederim.
2016

@dumb_programmer Yan not: lütfen kendinizi aptal deme. Imposter sendromu bu işte yaygındır, ancak programcının gerçek değeri "ne kadar bildiğini" değil, "ne kadar öğrenmeye istekli olduğunu" ifade eder. Bir şey anlamadınız, bu yüzden uzanıp sordunuz - bu mümkün olan en iyi eylemdir (ilk önce googling yaptıktan sonra).
Yksisarvinen

Evet her geçen gün daha iyiye gidiyorum! Cevabınız için teşekkürler @Yksisarvinen Yakında kullanıcı adımı değiştireceğim.
iyiProgrammer

0

Parametreleri değere göre geçiriyorsunuz. Referans olarak bunları geçmeniz gerekir:

template <typename T> void myswap(T& a , T& b);

Veya - daha genel olarak - küresel (değer) referansıyla:

template <typename T> void myswap(T&& a , T&& b);
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.