[英]Find All Palindrome Substrings in a String by Rearranging Characters
為了娛樂和練習,我嘗試解決以下問題(使用C ++): Given a string, return all the palindromes that can be obtained by rearranging its characters.
我想出了一種無法完全起作用的算法。 有時,它會找到所有回文,而在其他時候,它會發現一些但不是全部。
它通過將每對相鄰的字符對N
次交換來工作,其中N
是輸入字符串的長度。 這是代碼:
std::vector<std::string> palindromeGen(std::string charactersSet) {
std::vector<std::string> pals;
for (const auto &c : charactersSet) {
for (auto i = 0, j = 1; i < charactersSet.length() - 1; ++i, ++j) {
std::swap(charactersSet[i], charactersSet[j]);
if (isPalandrome(charactersSet)) {
if (std::find(pals.begin(), pals.end(), charactersSet) == pals.end()) {
// if palindrome is unique
pals.push_back(charactersSet);
}
}
}
}
return pals;
}
該算法有什么問題? 我最關心的是算法的功能,而不是效率。 盡管我也會感謝有關效率的提示。 謝謝。
這在“代碼審查”中可能更合適,但這里是:
您在迭代時更改charactersSet
,這意味着迭代器將中斷。 您需要復制characterSet
,並對其進行迭代。
由於pals
僅持有唯一值,因此應為std::set
而不是std::vector
。 這將簡化一些事情。 另外,您的isPalandrome
方法將回文拼寫錯誤!
由於回文僅能采用某種形式,因此請考慮首先對輸入字符串進行排序,以便您可以看到出現偶數的字符列表和出現奇數的字符列表。 您只能使用一個出現奇數次的字符(這僅適用於奇數長度的輸入)。 這應該讓您放棄很多可能性。 然后,您可以研究回文的一半的不同可能組合(因為您可以從另一半構建另一半)。
這是另一個利用std::next_permutation
:
#include <string>
#include <algorithm>
#include <set>
std::set<std::string> palindromeGen(std::string charactersSet)
{
std::set<std::string> pals;
std::sort(charactersSet.begin(), charactersSet.end());
do
{
// check if the string is the same backwards as forwards
if ( isPalindrome(charactersSet))
pals.insert(charactersSet);
} while (std::next_permutation(charactersSet.begin(), charactersSet.end()));
return pals;
}
我們首先對原始字符串進行排序。 這是std::next_permutation
正常工作所必需的。 在一個循環中調用帶有字符串置換的isPalindrome
函數。 然后,如果字符串是回文,則將其存儲在集合中。 隨后對std::next_permutation
調用只是重新排列了字符串。
這是一個實時示例 。 當然,它使用字符串的反向副本作為“ isPalindrome”函數(可能效率不高),但是您應該明白這一點。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.