C ++ кросс-платформенный код - PullRequest
       4

C ++ кросс-платформенный код

5 голосов
/ 10 августа 2010

Мы собираемся начать новый проект в нашей небольшой команде:

  • Это библиотека, которая будет использоваться другими нашими проектами (в Linux и Windows).
  • Это логически не зависит от платформы (не использует системные вызовы или что-то в этом роде).
  • Он должен быть скомпилирован на различных платформах (включая Windows и Linux как минимум).

К сожалению, ни один из наших разработчиков никогда не писал код на любой другой платформе, кроме Windows! Поэтому я должен дать им "код, подобный этому" или ", а не код, подобный этому" , так что код останется межплатформенным.

Любое руководство?

Ответы [ 7 ]

10 голосов
/ 10 августа 2010

Одним из способов повышения переносимости является использование одного и того же компилятора GCC на обеих платформах.Если вы также используете ту же версию компилятора, вы, вероятно, избежите большинства, если не всех несовместимостей языка C ++ и стандартной библиотеки.Вы также можете использовать те же инструменты сборки, что и GNU make, что означает, что процесс сборки одинаков на обеих платформах.

Что касается несовместимости платформ - убедитесь, что их код не содержит, например:

#include <windows.h>
#include <unistd.h>
#include <sys/almost_anything.h>

, если это не сделано с помощью условной компиляции.

7 голосов
/ 10 августа 2010

Убедитесь, что у вас есть автоматизированные процессы сборки на всех платформах, и напишите модульные и автоматизированные функциональные тесты. По возможности запускайте автоматические ночные сборки и тесты. Это гораздо важнее, когда вы пишете кроссплатформенные библиотеки.

Я бы сделал противоположный ответ на один из других (не то, чтобы я думал, что это неправильно, просто другой подход), и если вы можете выбирать свои платформы, сделайте их как можно более разными. Например, сделайте один 32-битный MCVC и другой 64-битный GCC на Unix. Если у вас могут быть автоматизированные тесты и сборки, это быстро покажет проблемы переносимости.

Если возможно, пусть некоторые разработчики работают над одной платформой, а некоторые - над другой, а не завершают код на одной платформе, а затем "переносят" его на другую. Таким образом, они очень быстро научатся тому, что не следует делать, когда их коллеги придут, чтобы жаловаться, что что-то сломали.

Технически вещи, на которые стоит обратить внимание:

  • Не думайте, что целые 32-битные
  • Не думайте, что символы подписаны или не подписаны
  • Не думайте, что символы в ASCII
  • Не предполагайте ничего о порядке байтов данных или выравнивании
  • Минимизировать арифметику указателя. Вы ошибетесь только тогда, когда сделаете предположения, которые не удаются.
  • Помните, что имена файлов и каталогов работают на разных платформах по-разному. Если вам нужно только портировать на windows и unix, вам может это сойти с рук, но как только вы перенесетесь на две платформы, тогда следующий порт может быть для z-series или VMS, где эти вещи работают совсем по-другому.
6 голосов
/ 10 августа 2010

Самое главное: иметь автоматические сборки и тесты, работающие на всех поддерживаемых платформах, все время, чтобы сразу выбрать наиболее непереносимый (или просто неправильный) код.

Сам язык, Стандартная библиотека и Boost должны быть переносимы на любую широко используемую платформу (безусловно, современные версии Linux / GCC и Windows / MSVC). С подозрением относитесь к любому системному заголовочному файлу, оканчивающемуся на .h, и проверьте переносимость других библиотек, прежде чем принять решение об их использовании.

Сохраните документ о всех несовместимостях, с которыми вы сталкиваетесь, так что, надеюсь, вы будете делать каждую ошибку только один раз.

5 голосов
/ 10 августа 2010

Просто скажите им, чтобы они не использовали Windows API, и они должны быть хорошими.

Я бы также предложил увеличить уровень предупреждения / ошибки, если вы разрабатываете в Visual Studio, так как это помешает вам делать некоторые вещи, которые gcc (обычно) не позволяет, предполагая, что вы используете gcc дляскомпилировать для Linux.Вы также можете отключить расширения Visual Studio в настройках проекта.

Очевидно, что если кому-то нужно использовать что-то специфичное для платформы, они должны использовать определения, которые заменяют специфичный для платформы код в зависимости от платформы, на которой он компилируется.*

2 голосов
/ 10 августа 2010

Компиляция с максимально возможным количеством компиляторов, даже если только на ограниченном количестве платформ.С головы до головы, ВК, gcc, intel, pgi.Если вы можете получить более старые версии некоторых из них, это также поможет.Всем разработчикам не нужно их использовать, но запускайте их по ночам с результатами, доступными для всех разработчиков.Гораздо проще исправлять проблемы по мере их появления, чем пытаться исправить все проблемы, когда вы пытаетесь их решить.

1 голос
/ 10 августа 2010

Некоторые предложения:

  • Используйте static_cast<>, dynamic_cast<> и const_cast<> вместо приведений в стиле C. Если необходимо использовать reinterpret_cast<>, просмотрите его и окружите этот код тщательными модульными тестами. (Смысл этого правила состоит в том, чтобы запретить хитрое переключение битов и полагаться на размеры или выравнивание.)

  • Используйте только современные стандартные библиотеки C ++: нет специфичных для MS библиотек, таких как (brrr!) MFC и его CString.

Вы можете добавить некоторые рекомендации здесь , но имейте в виду, что некоторые из них слишком пессимистичны для разумно современных компиляторов (например, рекомендация № 16 по временным объектам, а № 18 напрямую конфликтует с STL части библиотеки).

0 голосов
/ 10 августа 2010

Из опыта разработки под Linux среди разработчиков Windows, основной проблемой обычно (при условии, что вы действительно не используете платформо-зависимый код, как вы говорите) является только чувствительность к регистру в именах файлов #include. Кроме того, вы обнаружите, что gcc по умолчанию более строгий, чем MSVC, и поэтому вам, возможно, придется несколько усложнить, но обычно они довольно просты.

Одна особая вещь, на которую следует обратить внимание, это то, что std::map::erase не возвращает итератор .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...