मैं वर्तमान में इस कोड को सक्रिय करने और चलाने के लिए है:पाशन द्वारा C++ का मेल मानक एल्गोरिदम केवल एक बार
string word="test,";
string::iterator it = word.begin();
for (; it != word.end(); it++)
{
if (!isalpha(*it)) {
break;
}
else {
*it = toupper(*it);
}
}
word.erase(it, word.end());
// word should now be: TEST
मैं चाहूँगा यह अधिक कॉम्पैक्ट और पठनीय द्वारा इसे बनाने के लिए:
- मौजूदा मानक सी लिखना ++ एल्गोरिदम (*)
- केवल एक बार पाश प्रदर्शन करना
(*) मैं यह सोचते हैं रहा है कि ग मौजूदा एल्गोरिदम ombining मेरी कोड अधिक पठनीय बनाता है ...
एक वैकल्पिक समाधान
एक कस्टम transform_until
एल्गोरिथ्म को परिभाषित करने, के रूप में ज्रोक ने सुझाव दिया करने के लिए इसके अलावा, यह एक कस्टम इटरेटर एडाप्टर का उपयोग कर पुनरावृति हैं परिभाषित करने के लिए संभव हो सकता है अंतर्निहित पुनरावर्तक लेकिन इसे वापस करने से पहले अंतर्निहित संदर्भ को संशोधित करके ऑपरेटर *() को फिर से परिभाषित करें। कुछ इस तरह:
template <typename Iterator, typename UnaryFunction = typename Iterator::value_type (*)(typename Iterator::value_type)>
class sidefx_iterator: public std::iterator<
typename std::forward_iterator_tag,
typename std::iterator_traits<Iterator>::value_type,
typename std::iterator_traits<Iterator>::difference_type,
typename std::iterator_traits<Iterator>::pointer,
typename std::iterator_traits<Iterator>::reference >
{
public:
explicit sidefx_iterator(Iterator x, UnaryFunction fx) : current_(x), fx_(fx) {}
typename Iterator::reference operator*() const { *current_ = fx_(*current_); return *current_; }
typename Iterator::pointer operator->() const { return current_.operator->(); }
Iterator& operator++() { return ++current_; }
Iterator& operator++(int) { return current_++; }
bool operator==(const sidefx_iterator<Iterator>& other) const { return current_ == other.current_; }
bool operator==(const Iterator& other) const { return current_ == other; }
bool operator!=(const sidefx_iterator<Iterator>& other) const { return current_ != other.current_; }
bool operator!=(const Iterator& other) const { return current_ != other; }
operator Iterator() const { return current_; }
private:
Iterator current_;
UnaryFunction fx_;
};
बेशक यह अभी भी बहुत कच्चे है, लेकिन यह पता चलना चाहिए कि। ऊपर अनुकूलक के साथ, मैं उसके बाद निम्न लिख सकते हैं:
word.erase(std::find_if(it, it_end, std::not1(std::ref(::isalpha))), word.end());
साथ
अग्रिम में परिभाषित (कुछ टेम्पलेट जादू से सरल किया जा सकता है) के बाद:
using TransformIterator = sidefx_iterator<typename std::string::iterator>;
TransformIterator it(word.begin(), reinterpret_cast<typename std::string::value_type(*)(typename std::string::value_type)>(static_cast<int(*)(int)>(std::toupper)));
TransformIterator it_end(word.end(), nullptr);
तो मानक को शामिल किया जाएगा ऐसा एडाप्टर मैं इसका उपयोग करूंगा, क्योंकि इसका मतलब यह होगा कि यह निर्दोष था, लेकिन चूंकि यह मामला नहीं है, इसलिए शायद मैं अपना लूप रखूंगा।
इस तरह के एक एडाप्टर मौजूदा एल्गोरिदम और उन्हें अलग अलग तरीकों से मिश्रण आज संभव नहीं है पुन: उपयोग करने की अनुमति होगी, लेकिन यह रूप में अच्छी तरह कमियां हो सकता है, जो मैं संभावना पल में अनदेखी कर रहा हूँ ...
मेरे वर्तमान कोड में एक लूप है। मेरा मुद्दा यह था कि पुनर्लेखन के बाद भी एक लूप होगा। –
'isalpha (* it) 'पर आधारित समयपूर्व पलायन एकमात्र चीज है जो मैं आपको जो कुछ भी ढूंढ रहा हूं उसे प्राप्त करने से संभावित रूप से आपको रोक रहा हूं, और ईमानदारी से, जो कुछ भी आपके लिए कर सकता है (और मैं नहीं कर सकता तत्काल कुछ भी देखें जो संभवतः) इतनी गड़बड़ हो जाएगी कि आप स्पष्टता-कारक खिड़की से बाहर निकल जाएंगे। मैं आपके पास जो कुछ भी रखता हूं उसके साथ रहूंगा। – WhozCraig
आपके प्रेरणादायक उत्तरों के लिए सभी को धन्यवाद। मैं अभी के लिए अपने वर्तमान कोड के साथ रहना होगा। मेरा मानना है कि 'boost :: transform_iterator' निकटतम चीज़ है जिसे मैं ढूंढ रहा था। इस उपयोग के मामले को "साइड इफेक्ट्स" इटरेटर एडाप्टर द्वारा कवर किया जाएगा, इस तरह इस्तेमाल किया जाने वाला कुछ: 'word.erase (std :: find_if (sidefx_iterator (word.begin(), :: toupper), word.end (), std :: not1 (:: isalpha)), word.end()); ' –