COBOL
ID DIVISION.
PROGRAM-ID. BLOAT.
ENVIRONMENT DIVISION.
DATA DIVISION.
WORKING-STORAGE SECTION.
01 THE-TEST-STRINGS.
05 FILLER OCCURS 11584 TIMES.
10 TEST-STRING PIC X(11584).
LOCAL-STORAGE SECTION.
01 FIRST-TIME-FLAG PIC X VALUE "Y".
01 DISP-BEFORE-STRING COMP PIC 9(8).
01 LOOP-COUNTER COMP PIC 9(8).
01 START-STRING.
05 FILLER OCCURS 0 TO 11584 TIMES
DEPENDING ON DISP-BEFORE-STRING.
10 FILLER PIC X.
05 THE-SUBSTRING PIC X(12).
01 INITIAL-STRING PIC X(12)
VALUE "HELLO WORLD!".
LINKAGE SECTION.
01 STRING-PARAMETER PIC X(11584).
01 THE-RESULT PIC X.
PROCEDURE DIVISION USING
STRING-PARAMETER
THE-RESULT
.
IF FIRST-TIME-FLAG = "Y"
PERFORM SET-UP-STRINGS
END-IF
PERFORM
VARYING LOOP-COUNTER
FROM 1
BY 1
UNTIL LOOP-COUNTER
GREATER THAN 11584
OR STRING-PARAMETER
EQUAL TO TEST-STRING
( LOOP-COUNTER )
END-PERFORM
IF STRING-PARAMETER
EQUAL TO TEST-STRING ( LOOP-COUNTER )
MOVE "Y" TO THE-RESULT
ELSE
MOVE "N" TO THE-RESULT
END-IF
GOBACK
.
SET-UP-STRINGS.
PERFORM
VARYING LOOP-COUNTER
FROM 0
BY 1
UNTIL LOOP-COUNTER
EQUAL TO 11584
MOVE 11584 TO DISP-BEFORE-STRING
MOVE SPACE TO START-STRING
MOVE LOOP-COUNTER TO DISP-BEFORE-STRING
MOVE INITIAL-STRING TO THE-SUBSTRING
MOVE START-STRING TO TEST-STRING
( LOOP-COUNTER + 1 )
END-PERFORM
MOVE "N" TO FIRST-TIME-FLAG
.
Trochę wiedzy może być niebezpieczną rzeczą.
Szybsze może być wykonanie jednego dużego porównania niż wielu małych porównań; IBM COBOL dla przedsiębiorstw (do wersji 4.2) może mieć maksymalny czas przechowywania 128 MB (wersja 5.0 może mieć 2 GB); LOKALNE PRZECHOWYWANIE oferuje dodatkowe 128 MB, jeśli potrzebujesz więcej miejsca.
Zadanie polega na potwierdzeniu, że 11584-bajtowy element pamięci ma wartość „CZEŚĆ ŚWIATA!”. gdzieś, a reszta to przestrzeń.
Fikcyjny programista postanawia napisać w tym celu podprogram (na wypadek, gdyby był potrzebny gdzie indziej) i uwzględnić jego wysokowydajną technikę (premia).
Programista oblicza, że 11584 * 11584 ma 128 MB, więc używa WORKING-STORAGE dla ogromnego stołu i LOCAL-STORAGE dla wszystkiego, co jest potrzebne.
Programista koduje to i uśmiecha się do siebie świadomie, gdy kompilacja jest czysta. Mieli rację co do 128 MB.
Testuje kod. To działa. Być może trochę powolny, ale maszyna ma duże obciążenie. Uśmiecha się ponownie, myśląc, jak powolny byłby kod, gdyby nie posiadał poziomu wiedzy eksperckiej.
WORKING-STORAGE ma 134 189 056 bajtów, a także sporo innych bajtów. Powinien być wystarczająco duży.
Rzeczywistość jest taka, że wykonanie długiego porównania zamiast krótkiego porównania, tak jak tu zaimplementowano, jest bardzo powolnym sposobem.
Nawet wolniej, LOKALNE PRZECHOWYWANIE, które jest inicjowane przez procedury wykonawcze przy każdym wywołaniu podprogramu, powoduje skonfigurowanie całego 128 MB dla każdego POŁĄCZENIA.
Programista po prostu pomylił się co do wielkości stołu, jest wystarczająco dużo miejsca bez użycia LOCAL-STORAGE. Długie porównania mogą pokonać krótkie porównania, ale tylko wtedy, gdy faktyczna liczba porównań jest zmniejszona.
Zastanawiałem się nad zamianą LOKALNEGO PRZECHOWYWANIA i PRACY-PAMIĘCI, jest o wiele mniej prawdopodobne, że ktoś by to kodował w ten sposób, więc nie zrobiłem tego. Umieszczenie WARTOŚCIOWEJ MIEJSCA na stole (gdyby było to LOKALNE PRZECHOWYWANIE) zainicjowałoby tabelę dwa razy przy każdym POŁĄCZENIU, więc nawet wolniej.
Wzdęcia nie można usunąć bez przepisania programu. Większość kodu jest zła, choć istnieje jedna przydatna technika.
To nie jest prawdziwy przykład, ale mogę sobie wyobrazić, że ktoś to robi, jeśli jest wystarczająco sprytny :-)
Kompilacja nie stanowi żadnego problemu. Uruchamianie go z każdą możliwością szybko okazuje się nie warto próbować.
Oczywiście jest też zwykły stary Bug. Bardzo powszechny w zadaniach „wyszukiwania”.