Strona główna

Kurs pascala


Pobieranie 491.14 Kb.
Strona1/6
Data19.06.2016
Rozmiar491.14 Kb.
  1   2   3   4   5   6
KURS PASCALA

WSTĘP



Od autora

        Chciałbym wszystkim przypomnieć, że język Turbo Pascal (okrojony Borland Pascal 7.0) jest bardzo popularnym językiem programowania, przeznaczonym dla szrokiego kręgu odbiorców, przede wszystkim dla nieprofesjonalistów. Język Turbo Pascal, wbrew pozorom, nie jest wcale taki trudny do opanowania, można się go stosunkowo szybko nauczyć. Najczęściej jest on preferowany w szkołach średnich (uczą się go nawet studenci), stosowany jako "przedsmak" do języków jeszcze bardziej skomplikowanych tj. C/C++ czy Assebler.

        Kurs ten został napisany w dużej mierze na podstawie książki Andrzeja Marciniaka pt. "Turbo Pascal 7.0 z elementami programowania", z książki zaczerpnięte zostały poszczególne definicje elementów języka.

LEKCJA 1

Słowa kluczowe i dyrektywy języka

        W wersji 7.0 języka Turbo Pascal słowem kluczowym nazywamy każdy z 49. następujacych wyrazów języka angielskiego:



and

file

nil

shr

array

for

not

string

asm

function

object

then

begin

goto

of

to

case

if

or

type

const

implementation

packed

unit

constructor

in

procedure

until

destructor

inherited

program

uses

div

inline

record

var

do

interface

repeat

while

downto

label

set

with

else

mod

shl

xor

end

 

 

 

Słowa kluczowe są integralną częścią języka TP i są zastrzeżone, tzn. nie mogą być zdefiniowane przez programistę.

        Oprócz słów kluczowych w wersji 7.0 Pascal-a występują dyrektywy języka. Dyrektywą jest każdy z 10. następujących wyrazów:



absolute

far

near

public

assembler

forward

private

virtual

external

interrupt

 

 

W odróżnieniu od słów kluczowych, dyrektywy języka nie są zastrzeżone - podane wyrazy mogą więc być identyfikatorami zdefinowanymi przez programistę, co jednak nie jest zalecane. Penym wyjątkiem są dyrektywy private i public, które w obiektach (ale tylko w nich) są słowami zastrzeżonymi.

LEKCJA 2

Jak wygląda program w Pascalu ?

        Podstawowych pojęć jakimi się operuje programując w TP jest wprawdzie niewiele i nie są one trudne do zrozumienia, ale niewiedząc "z czym je jeść" nie mamy co zabierać się do programowania - wszystkie te pojęcia składają się na szkielet programu. Oto lista tych pojęć:

Struktura programu
Deklaracja modułów
Etykiety
Stałe
Typy danych
Zmienne
Procedury i funkcje

 

        Program napisany w TP 7.0 składa się z nagłówka programu (PROGRAM), deklaracji modułów, bloku i znaku . (kropka). W nagłówku programu podaje się zwykle jego nazwę. Za pomocą deklaracji modułów określa się moduły standardowe i moduły użytkownika. Blok składa się z opisu danych i części wykonawczej, a kropka kończy tekst programu. Dopuszcza się możliwość opuszczenia nagłówka (jest on pomijany przez kompilator), deklaracji modułów i opisu danych, a wiersz programu nie może zawierać więcej niż 127 znaków. Oto szkielet programu paskalowego:



 

PROGRAM Nazwa_Programu; {Nagłóewk programu}
USES {Deklaracja modułów}
{Początek części opisowej}
LABEL
CONST
TYPE
VAR
PROCEDURE
FUNCTION
{Koniec części opisowej}
BEGIN
{Część wykonawcza programu}
END.

 

 



        Deklaracja modułów (USES) jest klauzurą pozwalającą nam zdefiniować dowolną ilość modłów w naszym programie, np.

   USES CRT,DOS;

Powyższa deklaracja definiuje dla naszego programu dwa standardowe moduły DOS i CRT.

 

        Etykiety (LABEL) deklarujemy zaraz po deklaracji modułów klauzurą USES, powodują one skok do określonej części programu - wywołujemy je słowem kluczowym GOTO, np.



 

LABEL skok_1,skok_2;

...


BEGIN

GOTO skok_1;

...


...{Jakieś funkcje czy procedury.}

...


skok_1: Writeln('Skok do etykiety skok_1');

skok_2: Writeln('Skok do etykiety skok_2');



END.

 

Powyższy przykład obrazuje skok do etykiety skok_1. Podczas tej operacji omijane są wszelkie procedury i funkcje znajdujące się w wykropkowanych miejscach.



 

        Stałe (CONST) deklarujemy po deklaracji etykiet (LABEL), gdy zadeklarujemy jakąś stałą to w dalszej części programu nie możemy przypisać jej już innej wartości niż wartość początkowa. Zmiennym nie musimy przypisywać konkretnego typu danych, lecz w niektórych, bardziej złnożoych programach jest to wskazane, np.

 

CONST MaxWysokosc = 100;

MaxPredkosc = 10;

lub
CONST MaxWysokosc : Typ = Wartosc;

MaxPredkosc : Typ = Wartosc;

 

W drugim przykładzie Typ oznacza dowolny typ danych, wtedy wartość stałej przypisujemy zgodnie z typem.


        Typy (TYPE) deklarujemy po deklaracji stałych (CONST). Każdą zmienną w programie należy zadeklarować tzn. określić jej nazwę oraz wartości, które może ona przyjmować. Zbiór wartości zmiennej nazywa się typem zmiennej. Typy dzielimy na standardowe (predefiniowane, nie wymagające opisu) i niestandardowe (wprowadzane ręcznie przez programistę). O typach będzie jeszcze mowa w następnych lekcjach, więc podam tu tylko przykłady, np.

 

TYPE Dzien = (pon, wt, sr, czw, pt, sob, nie);

Numer = Integer;


        Zmienne (VAR) deklarujemy po deklaracji typów (TYPE). Jak już wspomniałem, wszystkie zmienne używane w programie powinny być zadeklarowane. Deklaracje zmiennych składają się ze słowa kluczowego VAR, po którym następuje wykaz deklaracji. Każdą zadeklarowaną zmienną (wartość zmiennej) możemy w głebi programu dowolnie definiować (przypisywać jej inne wartości), np.

 

VAR Wynik = Byte;

...


BEGIN

Wynik:=0; {Wartość początkowa}

...

Wynik:=10; {Wartość przypisana później}



END.

        Procedurę (PROCEDURE) lub funkcję (FUNCTION) deklarujemy po deklaracji zmiennych (VAR). Są to wyodrębnione części programu, stanowiące pewną całość, posiadające jednoznaczną nazwę i ustalony sposób wymiany informacji z pozostałymi częściami programu. Procedury i funkcje są stosowane do wykonania czynności, które mogą być wykorzystane w różnych programach lub do wykonania czynności wielokrotnie powtarzanych przez dany program. Różnica pomiędzy procedurą a funkcją polega na sposobie przekazywania wartości. Zadaniem procedury jest wykonanie pewnej sekwencji czynności, polegających zwykle na obliczaniu jedej lub wielu wartości. Natomiast zadaniem funkcji jest obliczenie jedej wartości (typu prostego lub wskaźnikowego). Odmienne są też sposoby wywołania procedur i funkcji, np.

 

Definicja procedury:


PROCEDURE Nazwa_Procedury(lista_parametrów);

...Część_opisowa



BEGIN

...Ciąg_instrukcji



END;
W definicji procedury listę parametrów możemy pominąć.
Definicja funkcji:
FUNCTION Nazwa_Funkcji(lista_parametrów): Typ_wyniku;

...Część_opisowa



BEGIN

...Ciąg_instrukcji



END;

 

W obu przypadkach lista parametrów zawiera deklarację parametrów, przy czym poszczególne deklaracje oddziela się średnikami. W przypadku funkcji w ciągu instrukcji musi wystąpić co najmniej jedna instrukcja przypisania w postaci:



 

Nazwa_Funkcji:=Wyrażenie

powodująca przypisanie wartości pod nazwę funkcji, przy czym co najmniej jedna z tych instrukcji musi być wykonana po wywołaniu funkcji. Typ wyniku funkcji jest określony za pomocą identyfikatora typu.

 LEKCJA 3



Typy danych i ich krótki opis

        Co to jest mniej więcej "typ" pisałem w poprzednim dziale, a w niniejszym opiszę dość dokładnie poszczególne typy wraz ze sposobami ich definicji w programie.

Podział typów danych:

 

 Typy proste



 Typy porządkowe

 Typ wyliczeniowy


 Typy całkowite
 Typy logiczne
 Typ znakowy
 Typy okrojone

 Typy rzeczywiste

 Typy łańcuchowe
 Typy strukturalne

 Typy tablicowe


 Typ rekordowy
 Typ zbiorowy
 Typ plikowy

 Typy wskaźnikowe


 Typy proceduralne
 Typ obiektowy

 

        Typy proste są podstawowymi typami języka Turbo Pascal i za ich pomocą określa się bardziej złożone struktury danych. Wszystkie typy proste składają się ze skończonego i uporządkowanego zbioru wartości. Dzięki temu na wartościach tych typów możemy m.in. wykonywać operacje porównań. Typy proste dzielimy na typy porządkowe i typy rzeczywiste.



 

        Typami porządkowymi nazywamy wszystkie typy proste z wyjątkiem typów rzeczywistych. Wyróżnienie to jest spowodowane faktem, że typy rzeczywiste często nie mogą występować w kontekście dozwolonym dla innych typów prostych. Dla wartości każdego typu porządkowego są określone wartości poprzednie i następne (z wyjątkiem wartości krańcowych). Do typów porządkowych zaliczamy: typ wyliczeniowy, typy całkowite, logiczne, typ znakowy i typy okrojone.

 

        Typ wyliczeniowy stosuje się zwykle dla zbiorów o niewielkiej liczbie elementów, na których nie wykonuje się operacji arytmetycznych. Definicja jednego typu wyliczeniowego jest następująca:



   TYPE identyfikator_typu = (lista_identyfikatorów);

Elementy typu wyliczeniowego są uporządkowane zgodnie z kolejnością ich wyliczenia w definicji typu i posiadają liczby porządkowe odpowiednio 0,1,2 itd.

 

Przyklady:


TYPE Uczniowie = (Antek, Franek, Zenek);

{Antek ma 0, Franek ma 1, a Zenek 2}

P_roku = (wiosna, lato, jesien, zima);

 

        Typy całkowite są w języku TP predefiniowane i nie wymagają opisu w programie. Wszystkie typy całkowite są podzbiorami zbioru liczb całkowitych. Wśród typów całkowitych wyróżniamy:



 

 ShortInt, przedział od -128 do 127


 Byte, przedział od 0 do 255
 Integer, przedział od -32768 do 32767
 Word, przedział od 0 do 65535
 LongInt, przedział od -2147483648 do 2147483647

 

 



Przyklad:
Przypuśćmy, że zdefiniowaliśmy nowy typ:
TYPE Liczba = Integer;
W takim razie poniższa deklaracja
VAR i,j: Liczba;
jest równoważna deklaracji
VAR i,j: Integer;

 

        Standardowymi typami logicznymi są typy Boolean, ByteBool, WordBool i LongBool. Wartości typów logicznych są oznaczone za pomocą dwu predefiniowanych literałów (stałych): True i False, oznaczających odpowiednio wartości logiczne fałsz i prawda, przy czym w sensie uporządkowania stała False poprzedza stałą True. Liczbami porządkowymi elementów typu Boolean są tylko 0 (False) i 1 (True). Elemanty pozostałych typów logicznych mogą posiadać inne (wyższe) liczby porządkowe.



 

        Do oznaczenia typu znakowego służy predefiniowany identyfikator Char. Elementami typu znakowego są znaki ASCII, z których każdy jest pamiętany w jednym bajcie pamięci.

 

        Typy okrojone służą do ograniczania zakresów wartości dowolnego z dotychczas opisanych typów porządkowych. Definicja jednego typu okrojonego ma postać



   TYPE identyfikator_typu = stała .. stała;

Pierwsza stała podaje ograniczenie dolne i nie może być większa od drugiej - ograniczenia górnego. Stałe te muszą być tego samego typu porządkowego.

 

Przyklad:


TYPE Litery = 'A' .. 'Z';

 

        Do typów prostych należą także standardowe typy rzeczywiste, które jednak nie są typami porządkowymi. Każdy z dostępnych typów rzeczywistych jest dyskretnym i skończonym podzbiorem zbioru liczb rzeczywistych. Dostępnych jest pięć standardowych typów rzeczywistych o następujących predefiniowanych identyfikatorach:



 

 Real, elementy zajmują po 6 bajtów pamięci


 Single, typ o pojedyńczej długości (4 bajty pamięci)
 Double, typ o podwójnej długości (8 bajtów pamięci)
 Extended, typ o rozszerzonej długości (10 bajtów pamięci)
 Comp, elementy to liczby całkowite z przedziału od -263+1 do 263-1

 

        Typy łańcuchowe służą do reprezentowania ciągu znaków, w tym niewidocznego znaku spacji. Elementami typu łańcuchowego są łańcuchy o długości od 0 do długości podanej w definicji typu łańcuchowego. Typ ten definiuje się następująco:



   TYPE identyfikator_typu = String[rozmiar];

lub


   TYPE identyfikator_typu = String;

gdzie rozmiar jest liczbą typu Byte. Brak wyspecyfikowania rozmiaru powoduje domyślne przyjęcie długości 255 znaków (warość maksymalna).

 

Przykład:


TYPE Nazwisko = String[20];

        Typy stukturalne stosuje się do opisu obiektów złożonych, przy czym dany obiekt możemy opisać na kilka róznych sposobów. Każdy z typów strukturalnych definiowany jest przez podanie typów składowych i metody strukturalizacji, która zarazem określa sposób dostępu do elementów składowych. W ogólności definicja pojedyńczego typu strukturalnego ma postać:

   TYPE Identyikator_typu = Opis_typu_strukturalnego;

przy czym opis typu strukturalnego może być opisem typu tablicowego, rekordowego, zbiorowego lub plikowego.

        Typ tablicowy, a konkretnie tablica składa się z ustalonej liczby elementów tego samego typu, zwanego typem składowym, który może być zarówno typem prostym lub łańcuchowym, jak i typem strukturalnym. Za pomocą tablic są reprezentowane regularne układy danych, np. wektory i macierze. Dostęp do poszczególnych elementów tablic uzyskuje się za pomocą indeksowania. Indeksem może być dowolne wyrażenie, którego wartość jest zgodna w sensie przypisania z typem indeksowym. Dopuszczalny zakres indeksów jest podany w definicji typu tablicowego. Definicja pojedynczego typu tablicowego ma postać:

   TYPE Identyfikator_typu = array[typy_indeksowe] of typ_składowy;

gdzie typy indeksowe są opisami typu porządkowego (z wyjątkiem typu LongInt), przy czym poszczególne opisy oddziela się przecinkami. Typ składowy oznacza dowolny typ.

 

 



Przykłady:
TYPE Macierz = array[1..20,1..30] of Real;

Tablica = array[Boolean,1..20,znak] of Char;

 

        Typem rekordowym, a dokładniej rekordem nazywamy złożoną strukturę danych, której składowe, zwane polami, mogą mieć rózne charakterystyki (należeć do różnych typów). Poszczególne pola mogą być same strukturami złożonymi, przy czym liczba pól rekordu jest ustalona. Definicja typu rekordowego określa typ i identyfikator dla każdego pola. Definicja ta rozpoczyna się słowem kluczowym record, po którym podaje się deklarację każdego pola, a kończy słowem kluczowym end. Poszczególne deklaracje pól oddziela się średnikami. Ostatnia deklaracja może być wariantowa (case .. of). Definicja pojedynczego typu rekordowego ma postać:



 

TYPE Identyfikator_typu = record

Lista_deklaracji_pól



end;

 

gdzie każda z deklaracji pól ma postać:



 

lista_nazw_pól : opis_typu;

 

a ostatnia deklaracja może mieć postać (deklaracja wariantowa):



 

case deklaracja_pola_wyróżnikowego of wykaz_wariantów;

 

lub



 

case identyfikator_typu_porządkowego of wykaz_wariantów;

 

przy czym deklaracja pola wyróżnikowego wygląda następująco:



 

identyfikator_pola_wyróżnikowego :

identyfikator_typu_porządkowego;

 

lub



 

lista_etykiet_wyboru : (lista_deklaracji_pól);

 

Przykłady rekordów:



 

TYPE Data = record

rok : Integer;

miesiac : 1 .. 12;

dzien : 1 .. 31;



end;
TYPE Rejestry = record

case Integer of

1: (AX, BX, CX, DX : Word);

2: (AL, AH, BL, BH, CL, CH,

DL, DH : Byte);



end;

end;

 

        Typ zbiorowy jest zbiorem potęgowym danego typu porządkowego, tzn. jest zbiorem wszystkich podzbiorów tego typu, w tym zbioru pustego. Liczba elementów typu zbiorowego nie może przekraczać 256 (przedział od 0 do 255). Definicja pojedynczego typu zbiorowego ma postać:



 

TYPE Identyfikator_typu = set of typy_porządkowy;

 

Przykład:



 

TYPE Klasy = set of (LO_1d, LO_2d, LO_3d,LO_4d);

 

ementami typu Klasy może być dowolny podzbiór zbioru podanych nazw klas, m.in.:



[ LO_1d, LO_2d ] - podzbiór dwuelementowy
[ LO_3d ] - podzbiór jednoelementowy
[ ] - zbiór pusty
[ LO_1d, LO_2d, LO_3d, LO_4d ] - podzbór czteroelementowy

        Typy plikowe są ściśle powiązane z plikami. Plik jest ciągiem elementów tego samego typu, tyle że liczba jego składowych jest zmienna. Jest ona uzależniona od przebiegu wykonywania programu, a w szczególności od skojarzenia pliku z fizycznym zbiorem danych. Od tablicy plik różni się ponadto metodą dostępu do poszczególnych elementów. Definicja pojedynczego typu plikowego ma postać:

 

TYPE Identyfikator_typu = file of opis_typu_elementów_pliku;

 

lub



 

TYPE Identyfikator_typu = file;

 

Jeżeli w definicji typu plikowego pominięto słowo kluczowe of i opis typu jego elementów, to przyjmuje się, że dany typ plikowy jest niezdefiniowany. Niezdefiniowane pliki są stosowane głównie w celu dostępu do fizycznych zbiorów dyskowych zgodnie z ich wewnętrznym formatem. W Pascalu istnieje predefiniowany plik tekstowy o nazwie Text (standardowy typ plikowy).



Przykłady:

 

TYPE Dane = file of Integer;

Zbior = file;

Wyniki = Text;

 

        Typy wskaźnikowe. Zmienne dotychczas omówionych typów, tj. typów prostych i strukturalnych, charakteryzują się tym, że istnieją przez cały czas wykonywania tej części , w której są zadeklarowane. Są to tzw. zmienne statyczne. W języku Turbo Pascal występują też zmienne dynamiczne reprezentujące obiekty, dla których pamięć jest przydzielana i zwalniana na okreśolne żądanie. Zmienne te nie posiadają identyfikatorów, a odwołanie do nich następuje za pomocą wskaźnika. Wartościami wskaźników są elementy typu wskaźnikowego, które określają adresy pamięci zmiennych dynamicznych. Zastosowanie w programie zmiennych dynamicznych pociąga za sobą konieczność zdefiniowania odpowiednich typów wskaźnikowych. Definicja pojedynczego typu wskaźnikowego ma postać:



 

TYPE Identyfikator_typu = ^Identyfikator_typu_bazowego;

 

Poprzyjmy to przykładem:



 

TYPE wskaznik = ^zapis;

zapis = record

Tekst: String[80];

Liczba: Integer;



end;

 

Definicja ta wiąże typ wskaznik ze zbiorem wskazań danych typu zapis. Jeśli wprowadzimy teraz deklarację:



 

VAR adres : wskaznik;

 

to zmiennej wskażnikowej adres będą mogły być w programie przypisywane adresy pamięci danych typu zapis.



W Pascalu występują dwa predefiniowane typy wskaźnikowe są to typy Pointer (zmienne tego typu są zgodne z dowolnym innym typem wskaźnikowym) i PChar (reprezentuje wskaźnik do łańcuchów zakończonych znakiem pustym).

Jednym ze słów kluczowych jest słowo nil, które oznacza stałą typu wskaźnikowego nie określającą żadnego adresu (nil wskazuje na adres pusty).

 

        Procedury i funkcje mogą być traktowane nie tylko jako części programu wykonywane na skutek wywołania, ale także jako elementy, które mogą być przypisywane do zmiennych i przekazywane do innych funkcji lub procedur jako parametry. Zmienne tego rodzaju powinny być typu proceduralnego Definicja pojedynczego typu proceduralnego może mieć jedną z następujących postaci:



 

TYPE Nazwa = procedure;

 

lub



 

TYPE Nazwa = procedure(lista_parametrów);

 

lub



 

  1   2   3   4   5   6


©snauka.pl 2016
wyślij wiadomość