(defun num-cmp (a b) (< a b)) ;; Функция сравнения для символов (defun sym-cmp (a b) (string< (string a) (string b))) ;; Генерация тестовых данных (defun generate-random-list (n) (loop repeat n collect (random 1000))) ;; ===================================================================== ;; Сортировка Шелла ;; Последовательность Седжвика (defun sedgewick-sequence (n) (labels ((sedgewick-iter (k seq) (let ((next (+ (* 4 (expt 2 k)) (* 3 (expt 2 (1- k))) 1))) (if (> next n) (reverse seq) (sedgewick-iter (1+ k) (cons next seq)))))) (if (<= n 1) '(1) (sedgewick-iter 1 '(1))))) ;; Сортировка вставками с шагом (defun insertion-sort-step (lst step cmp) (let ((n (length lst))) (loop for i from step below n do (let ((temp (nth i lst)) (j i)) (loop while (and (>= j step) (funcall cmp temp (nth (- j step) lst))) do (setf (nth j lst) (nth (- j step) lst)) (decf j step)) (setf (nth j lst) temp)))) lst) ;; Основная функция сортировки Шелла (defun shell-sort (lst cmp) (let ((n (length lst))) (if (<= n 1) lst (let ((steps (sedgewick-sequence n))) (shell-sort-with-steps lst steps cmp))))) ;; Сортировка с последовательностью шагов (defun shell-sort-with-steps (lst steps cmp) (if (null steps) lst (shell-sort-with-steps (insertion-sort-step lst (car steps) cmp) (cdr steps) cmp))) ;; Итеративная сортировка бинарными вставками (in-place) (defun binary-insertion-sort (list cmp) (let ((n (length list))) (loop for i from 1 below n do (let ((key (nth i list)) (left 0) (right i)) ;; Бинарный поиск позиции для вставки (loop while (< left right) do (let ((mid (floor (+ left right) 2))) (if (funcall cmp key (nth mid list)) (setf right mid) (setf left (1+ mid))))) ;; Сдвиг элементов вправо, чтобы освободить место (loop for j from i downto (1+ left) do (setf (nth j list) (nth (1- j) list))) ;; Вставка элемента (setf (nth left list) key)))) list) ;; Функция для тестирования (пример использования num-cmp) (defun test-binary-insertion-sort () (let ((test-list (list 5 2 8 1 9 4))) (format t "Original list: ~a~%" test-list) (let ((sorted-list (binary-insertion-sort (copy-list test-list) #'num-cmp))) ; Важно: copy-list (format t "Sorted list: ~a~%" sorted-list)))) ;; ===================================================================== ;; Тестирование (let* ((test-size 100) ; Размер списка можно менять (test-data (generate-random-list test-size))) ; Removed unnecessary copy (format t "Исходные данные (первые 10 элементов): ~a...~%" (subseq test-data 0 (min 10 (length test-data)))) (format t "~%Сортировка Шелла:~%") (time (shell-sort (copy-list test-data) #'num-cmp)) ; Создаем копию перед сортировкой (format t "~%Сортировка бинарными вставками:~%") (time (binary-insertion-sort (copy-list test-data) #'num-cmp))) ; Создаем копию перед сортировкой ;; Запуск теста (test-binary-insertion-sort)
Standard input is empty
Исходные данные (первые 10 элементов): (311 731 843 823 563 450 492 849 761 347)... Сортировка Шелла: Real time: 0.00705 sec. Run time: 0.007017 sec. Space: 2280 Bytes Сортировка бинарными вставками: Real time: 0.005023 sec. Run time: 0.004985 sec. Space: 1600 Bytes Original list: (5 2 8 1 9 4) Sorted list: (1 2 4 5 8 9)
Warning: reserving address range 0x80000c0000...0x1fffffffffff that contains memory mappings. clisp might crash later! Memory dump: 0x8000000000 - 0x80000bffff 0x14606fc00000 - 0x14606fee4fff 0x146070000000 - 0x146070002fff 0x146070003000 - 0x146070201fff 0x146070202000 - 0x146070202fff 0x146070203000 - 0x146070203fff 0x146070215000 - 0x146070239fff 0x14607023a000 - 0x1460703acfff 0x1460703ad000 - 0x1460703f5fff 0x1460703f6000 - 0x1460703f8fff 0x1460703f9000 - 0x1460703fbfff 0x1460703fc000 - 0x1460703fffff 0x146070400000 - 0x146070403fff 0x146070404000 - 0x146070603fff 0x146070604000 - 0x146070604fff 0x146070605000 - 0x146070605fff 0x146070634000 - 0x146070635fff 0x146070636000 - 0x146070645fff 0x146070646000 - 0x146070679fff 0x14607067a000 - 0x1460707b0fff 0x1460707b1000 - 0x1460707b1fff 0x1460707b2000 - 0x1460707b4fff 0x1460707b5000 - 0x1460707b5fff 0x1460707b6000 - 0x1460707b7fff 0x1460707b8000 - 0x1460707b8fff 0x1460707b9000 - 0x1460707bafff 0x1460707bb000 - 0x1460707bbfff 0x1460707bc000 - 0x1460707bcfff 0x1460707bd000 - 0x1460707bdfff 0x1460707be000 - 0x1460707cbfff 0x1460707cc000 - 0x1460707d9fff 0x1460707da000 - 0x1460707e6fff 0x1460707e7000 - 0x1460707eafff 0x1460707eb000 - 0x1460707ebfff 0x1460707ec000 - 0x1460707ecfff 0x1460707ed000 - 0x1460707f2fff 0x1460707f3000 - 0x1460707f4fff 0x1460707f5000 - 0x1460707f5fff 0x1460707f6000 - 0x1460707f6fff 0x1460707f7000 - 0x1460707f7fff 0x1460707f8000 - 0x146070825fff 0x146070826000 - 0x146070834fff 0x146070835000 - 0x1460708dafff 0x1460708db000 - 0x146070971fff 0x146070972000 - 0x146070972fff 0x146070973000 - 0x146070973fff 0x146070974000 - 0x146070987fff 0x146070988000 - 0x1460709affff 0x1460709b0000 - 0x1460709b9fff 0x1460709ba000 - 0x1460709bbfff 0x1460709bc000 - 0x1460709c1fff 0x1460709c2000 - 0x1460709c4fff 0x1460709c7000 - 0x1460709c7fff 0x1460709c8000 - 0x1460709c8fff 0x1460709c9000 - 0x1460709c9fff 0x1460709ca000 - 0x1460709cafff 0x1460709cb000 - 0x1460709cbfff 0x1460709cc000 - 0x1460709d2fff 0x1460709d3000 - 0x1460709d5fff 0x1460709d6000 - 0x1460709d6fff 0x1460709d7000 - 0x1460709f7fff 0x1460709f8000 - 0x1460709fffff 0x146070a00000 - 0x146070a00fff 0x146070a01000 - 0x146070a01fff 0x146070a02000 - 0x146070a02fff 0x55cc8e5fc000 - 0x55cc8e6ecfff 0x55cc8e6ed000 - 0x55cc8e7f6fff 0x55cc8e7f7000 - 0x55cc8e856fff 0x55cc8e858000 - 0x55cc8e886fff 0x55cc8e887000 - 0x55cc8e8b7fff 0x55cc8e8b8000 - 0x55cc8e8bbfff 0x55cc8f2e5000 - 0x55cc8f305fff 0x7ffcbeb0d000 - 0x7ffcbeb2dfff 0x7ffcbebf6000 - 0x7ffcbebf9fff 0x7ffcbebfa000 - 0x7ffcbebfbfff