Другие ответы тоже хороши, но случайное смешение побочных эффектов заставляет меня немного нервничать. Кроме того, у вас есть проблема, если список, который вы «анализируете», имеет свободную переменную (она станет 2
молча).
Почему бы не так:
is_two(X) :- X == 2, !, format("Yes").
is_two(X) :- X \== 2, !, format("No").
, а затем:
?- forall(member(X, [1,3,3,2,2,7,2,9]), is_two(X)).
NoNoNoYesYesNoYesNo
true.
?- forall(member(X, [Y, 2, Z]), is_two(X)).
NoYesNo
true.
Используйте ==
и \==
для сравнения без объединения. Используйте forall
и member
, чтобы прояснить, что вы делаете это для побочного эффекта. Обход списка (или использование maplist
) немного обманывает.
forall
- это просто более ясный способ сделать цикл, управляемый отказом, используя отрицание вместо сокращений и неудач. Вышеприведенный запрос идентичен:
?- \+ ( member(X, [1,3,3,2,2,7,2,9]), \+ is_two(X) ).
Вот то, что Википедия говорит по этому поводу (с некоторыми ссылками).
Похоже, что большую часть времени занимает просто загрузка данных (классов) с диска (т.е. время запуска ограничено вводом-выводом).
It really depends on what you are doing during the start up. If you run Hello World application it takes 0.15 seconds on my machine.
However, Java is better suited to running as a client or a server/service which means the startup time isn't as important as the connection time (about 0.025 ms) or the round trip time response time (<< 0.001 ms).
All VMs with a rich type system such as Java or CLR will not be instanteous when compared to less rich systems such as those found in C or C++. This is largely because a lot is happening in the VM, a lot of classes get initialized and are required by a running system. Snapshots of an initialized system do help but it still costs to load that image back into memory etc.
A simple hello world styled one liner class with a main still requires a lot to be loaded and initialized. Verifying the class requires a lot of dependency checking and validation all which cost time and many CPU instructions to be executed. On the other hand a C program will not do any of these and will amount of a few instructions and then invoke the printer function.
Запуск простого Java-приложения с клиентской JVM 1.6 (Java 6) на моем компьютере кажется мгновенным. Sun попыталась настроить клиентскую JVM для более быстрого запуска (и клиентская JVM используется по умолчанию), поэтому, если вам не нужно много дополнительных файлов jar, запуск должен быть быстрым.
Если вы используете Sun HotSpot для x86_64 (скомпилированный 64-битный), обратите внимание, что текущая реализация работает только в серверном режиме, то есть предварительно компилирует каждый загружаемый класс с полной оптимизацией, тогда как 32-битный версия также поддерживает клиентский режим, который обычно откладывает оптимизацию и оптимизирует только наиболее загруженные ЦП части, но имеет более быстрое время запуска.
См., например:
При этом, по крайней мере, на моей машине (Linux x86_64 с 64-битным ядром) 32-битный HotSpot версия поддерживает как клиентский, так и серверный режим (с помощью флагов -client и -server), но по умолчанию используется серверный режим, тогда как 64-битная версия поддерживает только серверный режим.
В дополнение к уже упомянутому (загрузка классов, особенно из сжатых JAR); работа в интерпретируемом режиме до того, как HotSpot скомпилирует обычно используемый байт-код; и накладные расходы на компиляцию HotSpot, существует также довольно много одноразовой инициализации, выполняемой самими классами JDK. Многие оптимизации сделаны в пользу более длительно работающих систем, где скорость запуска менее важна.
А что касается конвейерной обработки в стиле unix: вы, конечно, НЕ хотите запускать и перезапускать JVM несколько раз. Это не будет эффективным. Скорее объединение инструментов должно происходить внутри JVM. Это не может быть легко смешано с инструментами Unix, отличными от Java, за исключением запуска таких инструментов из JVM.
Существует ряд причин:
jar
s для загрузки Я не уверен насчет CLR, но я думаю, что часто она работает быстрее, потому что кэширует родную версию сборок для следующего раза (поэтому JIT не требуется). CPython запускается быстрее, потому что это интерпретатор, а IIRC не выполняет JIT.