2012-09-29 54 views
0

首先,我必須說,我正在向C++邁出第一步,而且我來自PHP,所以請原諒這個基本問題。我一直在尋找和測試許多替代品,我似乎無法理解如何做到這一點,在PHP中將如distance($str1, $str2)這樣的東西,以讀取任何功能distance返回。在C++中調用模板

我想要做的是調用一個模板,它應該返回2個字符串之間的Levenshtein距離。

這裏是我的代碼

template <class T> unsigned int edit_distance(const T& s1, const T& s2) 
{ 
    const size_t len1 = s1.size(), len2 = s2.size(); 
    vector<vector<unsigned int> > d(len1 + 1, vector<unsigned int>(len2 + 1)); 

    d[0][0] = 0; 
    for(unsigned int i = 1; i <= len1; ++i) d[i][0] = i; 
    for(unsigned int i = 1; i <= len2; ++i) d[0][i] = i; 

    for(unsigned int i = 1; i <= len1; ++i) 
     for(unsigned int j = 1; j <= len2; ++j) 

      d[i][j] = std::min(std::min(d[i - 1][j] + 1,d[i][j - 1] + 1), 
           d[i - 1][j - 1] + (s1[i - 1] == s2[j - 1] ? 0 : 1)); 
    return d[len1][len2]; 
} 

string text1="house"; 
string text2="houses"; 
edit_distance <int> (text1, text2); 

的問題是在線edit_distance <int> (text1, text2);和Xcode是給錯誤是:C++ requires a type specifier for all declarations

同樣,我知道這一定是非常基本的,但我不能找到正確的做法。 任何提示在正確的方向將不勝感激。

謝謝!

+0

您不要調用模板。您可以實例化它,並且可以調用該特定實例的某個成員函數(或靜態函數)。模板可以被理解爲一種生成(通過實例化)一些代碼的方式。他們不叫。 –

+4

爲什麼'',當輸入字符串? – kennytm

+0

謝謝巴西爾的更正。在這種情況下,我試圖調用edit_distance。 由於'edit_distance'返回的是一個整數,我認爲我應該用''調用它,但是再一次,這是我用C++的第一步,所以我很可能是錯誤的。同樣,當使用'string'時,構建失敗時會出現同樣的錯誤 – JimSim

回答

1

爲了測試我的疑惑,我帶了你的代碼,添加了最小包含和使用聲明,以便編譯器能夠調用edit_distance並編譯它。這裏是我編譯的文件的完整內容:

#include <vector> 
#include <string> 
#include <algorithm> 
using std::vector; 
using std::string; 

template <class T> unsigned int edit_distance(const T& s1, const T& s2) 
{ 
    const size_t len1 = s1.size(), len2 = s2.size(); 
    vector<vector<unsigned int> > d(len1 + 1, vector<unsigned int>(len2 + 1)); 

    d[0][0] = 0; 
    for(unsigned int i = 1; i <= len1; ++i) d[i][0] = i; 
    for(unsigned int i = 1; i <= len2; ++i) d[0][i] = i; 

    for(unsigned int i = 1; i <= len1; ++i) 
     for(unsigned int j = 1; j <= len2; ++j) 

      d[i][j] = std::min(std::min(d[i - 1][j] + 1,d[i][j - 1] + 1), 
           d[i - 1][j - 1] + (s1[i - 1] == s2[j - 1] ? 0 : 1)); 
    return d[len1][len2]; 
} 

string text1="house"; 
string text2="houses"; 
edit_distance <int> (text1, text2); 

我的懷疑被檢查出來;我得到了以下錯誤:

main.cpp:26:22: error: C++ requires a type specifier for all declarations 
edit_distance <int> (text1, text2); 
        ^~~~~ 

這是你提到確切的錯誤,因此,我認爲它很可能你已經犯同樣的錯誤,因爲我包含在我的測試源代碼。大多數有經驗的程序員會假設您的不完整代碼是爲了簡潔而顯示的,並且會自動插入一些完全避免此錯誤的周圍代碼。


你還沒有理解的東西似乎是在C++代碼不會去任何地方。 C++程序不是簡單的一系列語句,只要解釋器​​在源代碼中讀取它們就可以執行。

C++是一種編譯語言。該程序是一系列函數,類等的聲明和定義。語句,即執行內容的代碼僅在內部定義中使用。您的函數調用edit_distance<int>(text1, text2);不在任何定義之內,因此編譯器不期望發表聲明,也不知道您在說什麼。所以把它放在一個定義中。你可能想用一個函數的定義:

void foo() { 
    string text1="house"; 
    string text2="houses"; 
    edit_distance <int> (text1, text2); 
} 

另外,在執行編譯的代碼當執行在一個特殊的入口點函數開始,主。只有通過此入口點可到達的代碼才能執行。 (實際上這不是真的,但其他情況目前是不相關的。)

因此,您需要一個主函數,最終導致您要執行的代碼。你可以有main調用上述foo,或者你可以只是把你的代碼直接在main

int main() { 
    string text1="house"; 
    string text2="houses"; 
    edit_distance <int> (text1, text2); 
} 

此代碼仍然不能編譯,因爲<int>部分不正確。尖括號內的變型在edit_distance函數模板分配給T類型:

template <class T> unsigned int edit_distance(const T& s1, const T& s2) 

edit_distance<int>說要令T等於INT:

unsigned int edit_distance(const int& s1, const int& s2) 

而這不是你想要的。您可能希望將T設置爲字符串,以便s1和s2參數是字符串。

int main() { 
    string text1="house"; 
    string text2="houses"; 
    edit_distance<string>(text1,text2); 
} 

接下來你可能想要真正看到返回值。在源代碼開始添加#include <iostream>與您的其他包括,然後使用主要功能:

int main() { 
    string text1="house"; 
    string text2="houses"; 
    std::cout << edit_distance<string>(text1,text2) << '\n'; 
} 

Complete, compilable program

+0

非常感謝您的回覆和解答,這對我有很大幫助!是的,我沒有意識到事情如何在C++中編譯,這似乎與PHP中發生的事情有很大不同。再次感謝! – JimSim

1

template <class T> unsigned int edit_distance(const T& s1, const T& s2) 

的類型T可以直接從參數推斷。所以不需要指定類型。請致電

edit_distance(text1, text2); 

從一個函數內。您可以對模板支持的任何類型執行此操作。如果該類型不受支持,則會收到編譯時錯誤。

只有在無法推斷的情況下,才需要顯式指定類型。在你的情況下,你指定的類型<int>與你提供的參數不匹配。

+0

感謝Jon,正如你所說的那樣,問題在於我從外部調用函數(壞的PHP習慣),現在我學會了。感謝你的寶貴時間。 – JimSim