Почему GHC настолько большой/большой?


есть ли простой ответ: почему GHC такой большой?

  • OCaml: 2 МБ
  • Python: 15 МБ
  • SBCL: 9 МБ
  • OpenJRE-26MB
  • GHC: 113MB

не заинтересован в евангелизации "почему я не должен заботиться о размере, если Haskell является правильным инструментом"; это технический вопрос.

6 140

6 ответов:

Это немного глупо. Каждая библиотека, которая поставляется с GHC, предоставляется не менее чем 4 вкусы:

  • статический
  • динамический
  • профилированный
  • GHCi

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

помните, что GHC сам по себе является библиотекой, так что вы получаете 4 копии GHC. Не только это, но и сам двоичный файл GHC статически связан, так что это 5 копий GHC.

мы недавно сделали это так, что GHCi может использовать статический .a файлы. Это позволит нам избавиться от одного из этих ароматов. В долгосрочной перспективе мы должны динамически связывать GHC, но это большее изменение потому что это повлечет за собой динамическое связывание по умолчанию - в отличие от C, с GHC вы должны решить заранее, собираетесь ли вы связываться динамически или нет. И нам нужно больше изменений (например, для Cabal и системы пакетов, среди прочего), прежде чем это действительно практично.

наверное, надо сравнивать яблоки с яблоками и апельсины с апельсинами. JRE-это среда выполнения, а не комплект разработчика. Мы можем сравнить: исходный размер комплекта разработки, размер скомпилированного комплекта разработки и скомпилированный размер минимальной среды выполнения.

исходный пакет OpenJDK 7 составляет 82 МБ (download.java.net/openjdk/jdk7) vs GHC 7 source bundle, который составляет 23 Мб (haskell.org/ghc/download_ghc_7_0_1). GHC здесь не большой. Размер времени выполнения: openjdk-6-jre-headless на Ubuntu составляет 77 МБ несжатый vs Haskell helloworld, статически связанный со своей средой выполнения, которая составляет

где GHC большой, это размер скомпилированного комплекта разработки:

GHC disk usage

сам GHC занимает 270 МБ, а со всеми библиотеками и утилитами, которые собираются вместе, он занимает более 500 МБ. И да, это много, даже с базовыми библиотеками и инструментом сборки/менеджером зависимостей. Платформа разработки на Java меньший.

GHC:

$ aptitude show ghc6 | grep Size
Uncompressed Size: 388M

против OpenJDK с зависимостями:

$ aptitude show openjdk-6-jdk openjdk-6-jre openjdk-6-jre-headless ant maven2 ivy | grep Size
Uncompressed Size: 34.9M
Uncompressed Size: 905k
Uncompressed Size: 77.3M
Uncompressed Size: 1,585k
Uncompressed Size: 3,736k
Uncompressed Size: 991k

но это все еще больше, чем 100 МБ, а не 26 Мб, как вы пишете.

тяжеловесные вещи в ghc6 и ghc6-prof являются:

$ dpkg -L ghc6 | grep '\.a$' | xargs ls -1ks | sort -k 1 -n -r | head -3
57048 /usr/lib/ghc-6.12.1/ghc-6.12.1/libHSghc-6.12.1.a
22668 /usr/lib/ghc-6.12.1/Cabal-1.8.0.2/libHSCabal-1.8.0.2.a
21468 /usr/lib/ghc-6.12.1/base-4.2.0.0/libHSbase-4.2.0.0.a
$ dpkg -L ghc6-prof | grep '\.a$' | xargs ls -1ks | sort -k 1 -n -r | head -3
112596 /usr/lib/ghc-6.12.1/ghc-6.12.1/libHSghc-6.12.1_p.a
 33536 /usr/lib/ghc-6.12.1/Cabal-1.8.0.2/libHSCabal-1.8.0.2_p.a
 31724 /usr/lib/ghc-6.12.1/base-4.2.0.0/libHSbase-4.2.0.0_p.a

обратите внимание, насколько велик libHSghc-6.12.1_p.a. Таким образом, ответ, похоже, является статическим связыванием и профилированием версий для каждой библиотеки.

мое предположение -- много и много статических ссылок. Каждая библиотека должна статически связывать свои зависимости, которые, в свою очередь, должны статически связывать их и soforth. И все это часто компилируется как с профилированием, так и без него, и даже без профилирования двоичные файлы не удаляются и поэтому содержат много информации отладчика.

потому что он связывает gcc и куча библиотек, все статически.

по крайней мере на Windows.

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

динамическое соединение возможно и уменьшит размер драматически. Вот пример Hello.hs:

main = putStrLn "Hello world"

Я строю с GHC 7.4.2 на Windows.

ghc --make -O2 дает Hello.exe из 1105к

под управлением strip на нем листья 630 тыс.

ghc --make -O2 -dynamic дает 40K

зачистка оставляет всего 13к.

это ЗАВИСИМОСТИ 5 DLL с общим размером 9.2 MBs unstripped и 5.7 MB stripped.

вот разбивка размера каталога на моем поле:

https://spreadsheets.google.com/ccc?key=0AveoXImmNnZ6dDlQeHY2MmxPcEYzYkpweEtDSS1fUlE&hl=en

похоже, что самый большой каталог (123 Мб) - это двоичные файлы для компиляции самого компилятора. Документы весят в поразительном 65 МБ. Третье место-Cabal на 41 МБ.

каталог bin составляет 33 Мб, и я думаю, что только подмножество этого является технически необходимым для сборки Приложения на Haskell.