Middle
Ինչպիսի՞ն են C++-ում տողերով աշխատելու օպտիմալացման միջոցները։
sobes.tech AI
Պատասխան AI-ից
- Օգտագործել
std::string_view՝ տողերը փոխանցելու համար առանց տվյալների կրկնօրինակի: - Օգտագործել
<string>և<algorithm>գրադարանների ալգորիթմները (find,search) ձեռքով կրկնօրինակի փոխարեն: - Նախապես հատկացնել հիշողություն
reserve-ի միջոցով՝ նվազեցնելու համար վերաօգտագործումների թիվը տողի ընդլայնման ժամանակ: - Օգտագործել փոքր տողային բլոկ (Small String Optimization - SSO)
std::string-ում (եթե այն իրականացված է կոմպիլյատորով): - Երբ անհրաժեշտ է արագ միացման մեծ թվով տողեր, օգտագործել
std::stringstreamկամ ավելացնել տարր առ տարր՝ նախապես հատկացնելով տեղ: - Օգտագործել հատուկ գրադարաններ՝ տողերով աշխատելու համար, որոնք օպտիմիզացված են կոնկրետ խնդիրների համար (օրինակ, ռեգուլյար արտահայտություններ):
- Տողերը տեղադրել կայուն հիշողության կամ պուլում՝ խուսափելու համար դինամիկ հատկացմանից մշտական տողերով աշխատելիս:
- Օգտագործել ցածր մակարդակի C-շैलीի ֆունկցիաներ (
memcpy,memmove)՝ մեծ տվյալների ծավալների պատճենման համար, եթե դա անվտանգ և արդարացված է:
Օրինակ std::string_view-ի օգտագործման:
#include <string>
#include <string_view>
#include <iostream>
void print_string(std::string_view sv) {
std::cout << sv << std::endl;
}
int main() {
std::string s = "Hello, world!";
print_string(s); // Բացառապես առանց կրկնօրինակի
const char* c_str = "Նոր տող";
print_string(c_str); // Նույնպես առանց կրկնօրինակի
return 0;
}
Օրինակ reserve-ի օգտագործման:
#include <string>
#include <iostream>
int main() {
std::string s;
s.reserve(100); // Նախապես հատկացնել տեղ
for (int i = 0; i < 100; ++i) {
s += 'a'; // Ավելացնել նշաններ, քիչ վերաօգտագործումներ
}
std::cout << "Չափը: " << s.size() << ", Հավաքածու: " << s.capacity() << std::endl;
return 0;
}
Համեմատություն կոնկատենացիայի:
#include <string>
#include <sstream>
#include <iostream>
#include <chrono>
int main() {
const int count = 1000;
std::string chunk = "abc";
// Կոնկատենացի `+=` օպերատորով
auto start1 = std::chrono::high_resolution_clock::now();
std::string result1;
result1.reserve(count * chunk.size()); // Օպտիմիզացիա՝ նախապես հատկացնելով տեղ
for (int i = 0; i < count; ++i) {
result1 += chunk;
}
auto end1 = std::chrono::high_resolution_clock::now();
std::chrono::duration<double> elapsed1 = end1 - start1;
std::cout << "Օպերատոր += (առանց վերաօգտագործման): " << elapsed1.count() << " վայրկյան" << std::endl;
// Օգտագործել stringstream
auto start2 = std::chrono::high_resolution_clock::now();
std::stringstream ss;
for (int i = 0; i < count; ++i) {
ss << chunk;
}
std::string result2 = ss.str();
auto end2 = std::chrono::high_resolution_clock::now();
std::chrono::duration<double> elapsed2 = end2 - start2;
std::cout << "stringstream: " << elapsed2.count() << " վայրկյան" << std::endl;
return 0;
}
(Նշում՝ այս մեթոդների կատարողականությունը կարող է տարբերվել կոմպիլյատորից և ստանդարտ գրադարանից կախված):