spamsink: (Default)
[personal profile] spamsink

Дано:
using std::string;
string dotted_pair1(const string & a, const string & b) {
    return a + '.' + b;
}
string dotted_pair2(const string & a, const string & b) {
    return (a + '.') += b;
}

Как нетрудно видеть умозрительно, да и экспериментально, dotted_pair2 эффективнее - меньше временных объектов создается. В общем случае компилятор не имеет права делать такую оптимизацию автоматически. Как бы ему объяснить, что в этом конкретном случае он его имеет?

Ну и совсем абстрактно: интересно, программисты на ФЯП в принципе задумываются о зависимости эффективности выполняемого кода от идиоматики исходного, или они выше этих глупостей?

Date: 2012-08-24 06:52 pm (UTC)
From: [identity profile] rezkiy.livejournal.com
мне всегда казалось, что как только больше двух слагаемых, надо использовать что-то типа stringstream.

Date: 2012-08-24 07:03 pm (UTC)
From: [identity profile] rezkiy.livejournal.com
Надо профайлить.

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-24 07:29 pm (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-24 07:33 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 07:52 pm (UTC) - Expand
(deleted comment)

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 08:16 pm (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-24 08:38 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 08:42 pm (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-24 08:49 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 09:38 pm (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-24 10:29 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 10:33 pm (UTC) - Expand

(no subject)

From: [identity profile] rezkiy.livejournal.com - Date: 2012-08-24 10:14 pm (UTC) - Expand

Date: 2012-08-25 05:23 pm (UTC)
From: [identity profile] fatoff.livejournal.com
AFAIK, всего лишь избежать перераспределения памяти оптимизирует код достаточно сильно, чтобы к этой теме вообще возвращаться.

Вместо:

string dotted_pair1(const string & a, const string & b) {
return a + '.' + b;
}

Вот это:

string dotted_pair1(const string & a, const string & b) {
string s(a);
s.reserve(EXPECTED_LENGTH * 2);
s += ".";
s += b;
return s;
}

Ну и/или вместо возврата строки через return использовать неконстатную передачу объекта возвращаемой строки по ссылке. Но это банальщина...

Date: 2012-08-28 12:01 pm (UTC)
From: [identity profile] lazyreader.livejournal.com
string dotted_pair1(const string & a, const string & b) {
string s(a);
s.reserve(EXPECTED_LENGTH * 2);
s += ".";
s += b;
return s;
}


или, иначе говоря,
string dotted_pair1(string a, const string & b) {
a.reserve(EXPECTED_LENGTH * 2);
a += ".";
a += b;
return a;
}


Один из классиков недаром написал статью со спорным названием типа "хочешь скорости - передавай по значению!".
Edited Date: 2012-08-28 12:02 pm (UTC)

(no subject)

From: [identity profile] fatoff.livejournal.com - Date: 2012-08-28 02:09 pm (UTC) - Expand

Date: 2012-08-24 07:11 pm (UTC)
From: [identity profile] dvv.livejournal.com
gcc 4.1.2: апсолютно адинхуй.
gcc 4.7.1: апсолютно адинхуй.

Почему второй вариант вообще проходит — на первый взгляд непонятно.

Date: 2012-08-24 07:21 pm (UTC)
From: [identity profile] dvv.livejournal.com
Именно глядя на ассемблер.

Различия только вот в чём:

В первом случае пускается конструктор на временную строку с аргументом a, к ней цепляется одна точка, и ей же инициируется возврат, к возврату цепляется b. Деструктор на временную строку, выход из функции.

Во втором случае пускается конструктор на временную строку с аргументом a, к ней цепляется одна точка, к ей же цепляется b, ей же инициируется возврат. Деструктор на временную строку, выход из функции.

Возможно, из-за того, что конкатенации (append()) и конструктору приходится работать с разными данными, в профилировании может набежать разница. Но это уже от твоих данных зависит, а не от компилятора.
Edited Date: 2012-08-24 08:02 pm (UTC)

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-24 08:26 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 08:37 pm (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-24 08:42 pm (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-24 09:08 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 08:30 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 09:18 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 09:31 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 09:40 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 09:51 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 10:16 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 10:00 pm (UTC) - Expand

(no subject)

From: [identity profile] lazyreader.livejournal.com - Date: 2012-08-28 01:00 pm (UTC) - Expand

Date: 2012-08-24 07:22 pm (UTC)
From: [identity profile] mynine.livejournal.com
А на чем вы тестировали?
Я проверил VC2010 - практически идентичные варианты. По числу объектов совершенно одинаковые - один временный, где конкатенируются строки. Разница только в том что во втором случае временный объект создается явно внутри функции, а в первом через move внутри второго оператора конкатенации.

Date: 2012-08-24 07:44 pm (UTC)
From: [identity profile] mynine.livejournal.com
Чуть поторопился - в обоих случаях все-таки два объекта генерятся.

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 08:17 pm (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-24 09:18 pm (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-24 10:35 pm (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-24 11:36 pm (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-25 12:43 am (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-25 01:01 am (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-25 01:43 am (UTC) - Expand

(no subject)

From: [identity profile] dvv.livejournal.com - Date: 2012-08-25 02:08 am (UTC) - Expand

(no subject)

From: [identity profile] lazyreader.livejournal.com - Date: 2012-08-28 12:58 pm (UTC) - Expand

Date: 2012-08-24 07:46 pm (UTC)
From: [identity profile] cema.livejournal.com
В каком смысле исходного?

Date: 2012-08-24 09:01 pm (UTC)
From: [identity profile] sab123.livejournal.com
А небось printf в строку будет еще эффективнее.

Date: 2012-08-24 09:27 pm (UTC)
From: [identity profile] mynine.livejournal.com
я быстро проверил: проигрыш сишного варианта в два раза при оптимизации кода; без оптимизации быстрее раза в полтора.

(no subject)

From: [identity profile] rezkiy.livejournal.com - Date: 2012-08-24 10:12 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 10:15 pm (UTC) - Expand

(no subject)

From: [identity profile] rezkiy.livejournal.com - Date: 2012-08-24 10:21 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 10:30 pm (UTC) - Expand

(no subject)

From: [identity profile] rezkiy.livejournal.com - Date: 2012-08-24 10:56 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 11:15 pm (UTC) - Expand

(no subject)

From: [identity profile] rezkiy.livejournal.com - Date: 2012-08-25 01:13 am (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-25 08:23 am (UTC) - Expand

(no subject)

From: [identity profile] rezkiy.livejournal.com - Date: 2012-08-27 04:19 am (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-27 08:26 am (UTC) - Expand

(no subject)

From: [identity profile] rezkiy.livejournal.com - Date: 2012-08-27 08:58 am (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-27 09:04 am (UTC) - Expand

(no subject)

From: [identity profile] rezkiy.livejournal.com - Date: 2012-08-27 09:12 am (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-27 09:38 am (UTC) - Expand

(no subject)

From: [identity profile] rezkiy.livejournal.com - Date: 2012-08-27 09:04 am (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-27 09:10 am (UTC) - Expand

(no subject)

From: [identity profile] rezkiy.livejournal.com - Date: 2012-08-24 11:05 pm (UTC) - Expand

(no subject)

From: [identity profile] mynine.livejournal.com - Date: 2012-08-24 11:16 pm (UTC) - Expand

(no subject)

From: [identity profile] rezkiy.livejournal.com - Date: 2012-08-25 01:30 am (UTC) - Expand

Date: 2012-08-25 10:41 am (UTC)
From: [identity profile] fregimus.livejournal.com
«программисты на ФЯП в принципе задумываются о зависимости эффективности выполняемого кода от идиоматики исходного» — если задумываются, значит, язык дурной. Как C++, например. Читали The Rise Of Worse Is Better? Гениальный человек rpg написал — в таком быстро меняющемся мире программирования все предсказал абсолютно точно на 20 лет вперед.

Date: 2012-08-25 10:45 am (UTC)
From: [identity profile] fregimus.livejournal.com
Хотя… задумываются, конечно. В хаскеле, ML и лиспе присобачить голову к списку — O(1), a хвост — O(N) и памяти, и времени. Когда строят список, начиная с головы, то строят его в обратном порядке, а потом переворачивают. А в Математике, хоть она и ML-подобная, все иначе — но там свои трюки с оптимизацией.

Date: 2012-08-25 07:16 pm (UTC)
From: [identity profile] thesz.livejournal.com
http://stgcompiler.googlecode.com/svn/trunk/Docs/Artigos/fusion(strings).pdf

Чуть ли не самый известный пример, когда программисты на FP задумались о производительности. И каким образом она была достигнута.

Date: 2012-08-26 04:33 pm (UTC)
From: [identity profile] thesz.livejournal.com
Что интересно, ForeignPtr не совсем хорош: http://hackage.haskell.org/package/text-0.11.2.3 ;)

При больших объёмах текста в ByteString эта штука начинает фрагментировать кучу. Поэтому и был придуман text.

Date: 2012-08-25 09:40 pm (UTC)
From: [identity profile] besisland.livejournal.com
По второму вопросу хочу предположить, что такое в корне неправильно и может быть только лишь вынужденной мерой.

Date: 2012-08-28 12:04 pm (UTC)
From: [identity profile] lazyreader.livejournal.com
С новым стандартом могу вообразить

string operator+(string&& a, string&& b);


и умный компилятор, который сможет использовать этот факт в вычислениях типа

return a + '.' + b;

Profile

spamsink: (Default)
spamsink

February 2026

S M T W T F S
12345 67
8 91011 121314
15161718 192021
22 2324 25262728

Most Popular Tags

Style Credit

Expand Cut Tags

No cut tags
Page generated Mar. 5th, 2026 02:14 am
Powered by Dreamwidth Studios