Recent

Author Topic: [SOLVEd] How to make a queue in pascal  (Read 4424 times)

quake004

  • New Member
  • *
  • Posts: 33
[SOLVEd] How to make a queue in pascal
« on: April 13, 2020, 03:03:35 pm »
I'm trying to make an integer Queue class with the methods Create, Enqueue and Show. To insert items and show all the elements in the queue but I can't even compile the constructor.

Code: Pascal  [Select][+][-]
  1. unit TestQueue
  2.  
  3. interface
  4.  
  5. type TQueue = class
  6.   private
  7.     type SQueue = record
  8.       front, rear, size: Integer;
  9.       capacity: Byte;
  10.       content: Array of Integer;
  11.     end;
  12.     type PtrQueue = ^SQueue;
  13.   public
  14.     constructor Create(); overload;
  15.     constructor Create(capacity: Byte); overload;
  16.   end;
  17.  
  18. implementation
  19.  
  20. procedure Create();
  21. var
  22.   Queue: PtrQueue;
  23. begin
  24.   Queue := new(PtrQueue);
  25.   ^Queue.capacity := capacity;
  26.   ^Queue.front := 0;
  27.   ^Queue.rear := capacity - 1;
  28.   setLength(^Queue.content, capacity);
  29. end;
  30.  
  31. procedure Main();
  32. begin
  33.   Queue: TQueue = TQueue.Create();
  34. end;
  35.  
  36. BEGIN
  37.   Main();
  38. END.
  39.  
« Last Edit: April 15, 2020, 06:25:48 pm by quake004 »

eljo

  • Sr. Member
  • ****
  • Posts: 468
Re: How to make a queue in pascal
« Reply #1 on: April 13, 2020, 05:03:54 pm »
where is the PtrQueue type declared?

Next time please post the error message you get, it will help people answer you faster.
« Last Edit: April 13, 2020, 05:14:34 pm by eljo »

quake004

  • New Member
  • *
  • Posts: 33
Re: How to make a queue in pascal
« Reply #2 on: April 13, 2020, 05:58:19 pm »
I've declared the pointer just below the the SQueue structure. Is it ok what I'm doing of creating the structure inside the class or it isn't needed?
I'm compiling it with `fpc Queue.pas` and this is the error I'm getting:

Code: Pascal  [Select][+][-]
  1. 0/90]Free Pascal Compiler version 3.0.4+dfsg-18ubuntu2 [2018/08/29] for x86_64
  2. Copyright (c) 1993-2017 by Florian Klaempfl and others
  3. Target OS: Linux for x86-64
  4. Compiling Queue.pasQueue.pas(1,15) Error: Illegal unit name: TestQueue
  5. Queue.pas(7,15) Error: Identifier not found "class"
  6. Queue.pas(8,3) Error: Error in type definition
  7. Queue.pas(8,3) Fatal: Syntax error, ";" expected but "identifier PRIVATE" found
  8. Fatal: Compilation aborted
  9. Error: /usr/bin/ppcx64 returned an error exitcode
  10.  

eljo

  • Sr. Member
  • ****
  • Posts: 468
Re: How to make a queue in pascal
« Reply #3 on: April 13, 2020, 06:08:07 pm »
I've declared the pointer just below the the SQueue structure. Is it ok what I'm doing of creating the structure inside the class or it isn't needed?
I have no idea, declaring types inside a class its a concept I never understood or used.
I'm compiling it with `fpc Queue.pas` and this is the error I'm getting:

Code: Pascal  [Select][+][-]
  1. 0/90]Free Pascal Compiler version 3.0.4+dfsg-18ubuntu2 [2018/08/29] for x86_64
  2. Copyright (c) 1993-2017 by Florian Klaempfl and others
  3. Target OS: Linux for x86-64
  4. Compiling Queue.pasQueue.pas(1,15) Error: Illegal unit name: TestQueue
  5. Queue.pas(7,15) Error: Identifier not found "class"
  6. Queue.pas(8,3) Error: Error in type definition
  7. Queue.pas(8,3) Fatal: Syntax error, ";" expected but "identifier PRIVATE" found
  8. Fatal: Compilation aborted
  9. Error: /usr/bin/ppcx64 returned an error exitcode
  10.  
Now that tells the complete story to semi seasoned user like me. You did not specify the pascal dialect to be used and the compiler used the default dialect that does not support classes and the more modern constructs. try adding
Code: Pascal  [Select][+][-]
  1. {$MODE OBJFPC}
  2.  
on top of your unit right before the unit TestQueue; declaration. That should get you a bit farther.

quake004

  • New Member
  • *
  • Posts: 33
Re: How to make a queue in pascal
« Reply #4 on: April 13, 2020, 06:26:37 pm »
Ok now it seems it understands what the class word is. The rest of the error is mostly the same.

Code: Pascal  [Select][+][-]
  1. Free Pascal Compiler version 3.0.4+dfsg-18ubuntu2 [2018/08/29] for x86_64
  2. Copyright (c) 1993-2017 by Florian Klaempfl and othersTarget OS: Linux for x86-64
  3. Compiling Queue.pas
  4. Queue.pas(3,15) Error: Illegal unit name: TestQueue
  5. Queue.pas(22,1) Fatal: There were 1 errors compiling module, stopping
  6. Fatal: Compilation aborted
  7. Error: /usr/bin/ppcx64 returned an error exitcode
  8.  

bytebites

  • Hero Member
  • *****
  • Posts: 632
Re: How to make a queue in pascal
« Reply #5 on: April 13, 2020, 06:36:05 pm »
Replace
Code: Pascal  [Select][+][-]
  1. unit TestQueue
with
Code: Pascal  [Select][+][-]
  1. program TestQueue

quake004

  • New Member
  • *
  • Posts: 33
Re: How to make a queue in pascal
« Reply #6 on: April 13, 2020, 07:04:16 pm »
If I write program it tells me 'begin' expected but 'interface' found. And I want to use the class from other files so it should be a unit shouldn't it?

bytebites

  • Hero Member
  • *****
  • Posts: 632
Re: How to make a queue in pascal
« Reply #7 on: April 13, 2020, 07:16:38 pm »
Then you don't need main-procedure.
Unit name must be same as file name.
Declaration of procedure Create() must contains type
Code: Pascal  [Select][+][-]
  1. procedure TQueue.Create();

quake004

  • New Member
  • *
  • Posts: 33
Re: How to make a queue in pascal
« Reply #8 on: April 13, 2020, 07:29:07 pm »
But can I use Main procedure for testing or it doesn't work?

Code: Pascal  [Select][+][-]
  1. {$MODE OBJFPC}
  2.  
  3. unit TestQueue;
  4.  
  5. interface
  6.  
  7. uses Classes;
  8.  
  9. type TQueue = class
  10.   private
  11.     type SQueue = record
  12.       front, rear, size: Integer;
  13.       capacity: Byte;
  14.       content: Array of Integer;
  15.     end;
  16.     type PtrQueue = ^SQueue;
  17.   public
  18.     constructor Create; overload;
  19.     constructor Create(capacity: Byte); overload;
  20.   end;
  21.  
  22. implementation
  23.  
  24. procedure TQueue.Create();
  25. begin
  26.   Create(1000);
  27. end;
  28.  
  29. procedure TQueue.Create(capacity: Byte);
  30. var
  31.   Queue: PtrQueue;
  32. begin
  33.   Queue := new(PtrQueue);
  34.   ^Queue.capacity := capacity;
  35.   ^Queue.front := 0;
  36.   ^Queue.size := 0;
  37.   ^Queue.rear := capacity - 1;
  38.   setLength(^Queue.content, capacity);
  39. end;
  40.  
  41. procedure Main();
  42. var
  43.   Queue: TQueue;
  44. begin
  45.   Queue := TQueue.Create();
  46. end;
  47.  
  48. BEGIN
  49.   Main();
  50. END.
  51.  

Code: Pascal  [Select][+][-]
  1. Free Pascal Compiler version 3.0.4+dfsg-18ubuntu2 [2018/08/29] for x86_64Copyright (c) 1993-2017 by Florian Klaempfl and othersTarget OS: Linux for x86-64Compiling TestQueue.pasTestQueue.pas(24,18) Error: function header doesn't match any method of this class "Create;"
  2. TestQueue.pas(18,17) Error: Found declaration: constructor Create;TestQueue.pas(19,17) Error: Found declaration: constructor Create(Byte);TestQueue.pas(26,14) Warning: range check error while evaluating constants (1000 must be between 0 and 255)
  3. TestQueue.pas(29,18) Error: function header doesn't match any method of this class "Create(Byte);"
  4. TestQueue.pas(18,17) Error: Found declaration: constructor Create;
  5. TestQueue.pas(19,17) Error: Found declaration: constructor Create(Byte);TestQueue.pas(24,18) Error: Found declaration: Create;TestQueue.pas(34,5) Error: Illegal expression
  6. TestQueue.pas(34,5) Fatal: Syntax error, ";" expected but "identifier UEUE" found
  7. Fatal: Compilation aborted
  8. Error: /usr/bin/ppcx64 returned an error exitcode
  9.  

If I write constructor TQueue.Create; overload in the interface I get:
Code: Pascal  [Select][+][-]
  1. Free Pascal Compiler version 3.0.4+dfsg-18ubuntu2 [2018/08/29] for x86_64Copyright (c) 1993-2017 by Florian Klaempfl and othersTarget OS: Linux for x86-64
  2. Compiling TestQueue.pas
  3. TestQueue.pas(18,23) Fatal: Syntax error, ";" expected but "." found
  4. Fatal: Compilation aborted
  5. Error: /usr/bin/ppcx64 returned an error exitcode
  6.  
« Last Edit: April 13, 2020, 07:34:58 pm by quake004 »

eljo

  • Sr. Member
  • ****
  • Posts: 468
Re: How to make a queue in pascal
« Reply #9 on: April 13, 2020, 07:55:02 pm »
which IDE are you using? in lazarus there is a test project you can create with various features in order to test your classes. I guess that in the FP IDE must be something similar.

In short no don't mix program and unit code in the same file create a new file as a program and use the unit there for testing.

bytebites

  • Hero Member
  • *****
  • Posts: 632
Re: How to make a queue in pascal
« Reply #10 on: April 13, 2020, 08:09:33 pm »
procedure need to be constuctor
Code: Pascal  [Select][+][-]
  1. constructor TQueue.Create();

byte type is too small, use integer instead.

^Queue.capacity := capacity;

The hat is in the wrong end

Code: Pascal  [Select][+][-]
  1. Queue^.capacity := capacity;

quake004

  • New Member
  • *
  • Posts: 33
Re: How to make a queue in pascal
« Reply #11 on: April 13, 2020, 08:52:38 pm »
Finally it compiles. Thank you.

Code: Pascal  [Select][+][-]
  1. {$MODE OBJFPC}
  2.  
  3. unit TestQueue;
  4.  
  5. interface
  6.  
  7. uses Classes;
  8.  
  9. type TQueue = class
  10.   private
  11.     type SQueue = record
  12.       front, rear, size: Integer;
  13.       capacity: Integer;
  14.       content: Array of Integer;
  15.     end;
  16.     type PtrQueue = ^SQueue;
  17.   public
  18.     constructor Create; overload;
  19.     constructor Create(capacity: Integer); overload;
  20.   end;
  21.  
  22. implementation
  23.  
  24. constructor TQueue.Create();
  25. begin
  26.   Create(1000);
  27. end;
  28.  
  29. constructor TQueue.Create(capacity: Integer);
  30. var
  31.   Queue: PtrQueue;
  32. begin
  33.   Queue := new(PtrQueue);
  34.   Queue^.capacity := capacity;
  35.   Queue^.front := 0;
  36.   Queue^.size := 0;
  37.   Queue^.rear := capacity - 1;
  38.   setLength(Queue^.content, capacity);
  39. end;
  40.  
  41. procedure Main();
  42. var
  43.   Queue: TQueue;
  44. begin
  45.   Queue := TQueue.Create();
  46. end;
  47.  
  48. BEGIN
  49.   Main();
  50. END.
  51.  

I'm compiling it from the command line. I don't want to install an IDE just for a couple scripts I'm going to write.

howardpc

  • Hero Member
  • *****
  • Posts: 4144
Re: How to make a queue in pascal
« Reply #12 on: April 13, 2020, 10:40:37 pm »
Here's a simpler implementation to give you some ideas.
Code: Pascal  [Select][+][-]
  1. program TestQueue;
  2.  
  3. {$mode objfpc}{$H+}
  4.  
  5. type
  6.   TQueue = class(TObject)
  7.   private
  8.     FGrow: Integer;
  9.     FHeadIndex: Integer;
  10.     FQueue: array of Integer;
  11.     FTailIndex: Integer;
  12.     function GetPeekHead: Integer;
  13.     function GetCount: Integer;
  14.     function GetPeekTail: Integer;
  15.   public
  16.     constructor Create(anInitialGrow: Integer=16);
  17.     function IsEmpty: Boolean;
  18.     function LeaveOK(out UnQueuedValue: Integer): Boolean;
  19.     procedure Join(JoiningValue: Integer);
  20.     procedure Report;
  21.     property Count: Integer read GetCount;
  22.     property PeekHead: Integer read GetPeekHead;
  23.     property PeekTail: Integer read GetPeekTail;
  24.   end;
  25.  
  26. function TQueue.GetPeekHead: Integer;
  27. begin
  28.   if IsEmpty then
  29.     Result := -MaxInt
  30.   else Result := FQueue[FHeadIndex];
  31. end;
  32.  
  33. function TQueue.GetCount: Integer;
  34. begin
  35.   case FHeadIndex of
  36.     -1: Result := 0;
  37.     else Result := Succ(FTailIndex - FHeadIndex);
  38.   end;
  39. end;
  40.  
  41. function TQueue.GetPeekTail: Integer;
  42. begin
  43.   if IsEmpty then
  44.     Result := -MaxInt
  45.   else Result := FQueue[FTailIndex];
  46. end;
  47.  
  48. constructor TQueue.Create(anInitialGrow: Integer);
  49. begin
  50.   Assert(anInitialGrow<>0, 'TQueue.Create: capacity must be greater than zero');
  51.   FGrow := anInitialGrow;
  52.   SetLength(FQueue, anInitialGrow);
  53.   FHeadIndex := -1;
  54.   FTailIndex := FHeadIndex;
  55. end;
  56.  
  57. procedure TQueue.Join(JoiningValue: Integer);
  58. begin
  59.   case IsEmpty of
  60.     True:  begin
  61.              FTailIndex := 0;
  62.              FHeadIndex := 0;
  63.              FQueue[FTailIndex] := JoiningValue;
  64.            end;
  65.     False: begin
  66.              if FTailIndex >= High(FQueue) then
  67.                SetLength(FQueue, Length(FQueue) + FGrow);
  68.              Inc(FTailIndex);
  69.              FQueue[FTailIndex] := JoiningValue;
  70.            end;
  71.   end;
  72. end;
  73.  
  74. procedure TQueue.Report;
  75. begin
  76.   case IsEmpty of
  77.     True:  Writeln('Empty queue');
  78.     False: WriteLn('Count=',Count,' PeekHead=',PeekHead,' PeekTail=',PeekTail);
  79.   end;
  80. end;
  81.  
  82. function TQueue.LeaveOK(out UnQueuedValue: Integer): Boolean;
  83. begin
  84.   case IsEmpty of
  85.     True:  begin
  86.              UnQueuedValue := -MaxInt;
  87.              Result := False;
  88.            end;
  89.     False: begin
  90.              UnQueuedValue := FQueue[FHeadIndex];
  91.              Inc(FHeadIndex);
  92.              if Count = 0 then
  93.                begin
  94.                  FHeadIndex := -1;
  95.                  FTailIndex := FHeadIndex;
  96.                  if Length(FQueue) <> FGrow then
  97.                    SetLength(FQueue, FGrow);
  98.                end;
  99.              Result := True;
  100.            end;
  101.   end;
  102. end;
  103.  
  104. function TQueue.IsEmpty: Boolean;
  105. begin
  106.   Result := (FHeadIndex = -1) and (FHeadIndex = FTailIndex);
  107. end;
  108.  
  109. var
  110.   q: TQueue;
  111.   i, j, k, l, m, n, o, p: Integer;
  112.   canLeave: Boolean;
  113.  
  114. begin
  115.   q := TQueue.Create;
  116.   with q do
  117.     begin
  118.       Join(79);
  119.       Join(3);
  120.       LeaveOK(i);
  121.       Join(92);
  122.       Join(-40);
  123.       Join(100);
  124.       LeaveOK(j);
  125.       Join(1);
  126.  
  127.       Report;
  128.  
  129.       LeaveOK(k);
  130.       LeaveOK(l);
  131.       leaveOK(m);
  132.       Join(-2);
  133.       LeaveOK(n);
  134.       WriteLn('i=',i,'  j=',j,'  k=',k,'  l=',l,'  m=',m,'  n=',n);
  135.       WriteLn('q.Count=',q.Count,'  isEmpty is ',q.IsEmpty,'  peekhead=',q.PeekHead,'  peektail=',q.PeekTail);
  136.       LeaveOK(o);
  137.       canLeave := LeaveOK(p);
  138.       WriteLn('o=',o,'  canLeave is ',canLeave,'  isEmpty is ',q.IsEmpty);
  139.       Free;
  140.     end;
  141.   ReadLn;
  142. end.

quake004

  • New Member
  • *
  • Posts: 33
Re: How to make a queue in pascal
« Reply #13 on: April 14, 2020, 03:25:44 pm »
Thanks a lot. I was just trying to remove the struct because I had pointers everywhere and there was no advantage at all. What does the F stand for in the private variables?

howardpc

  • Hero Member
  • *****
  • Posts: 4144
Re: How to make a queue in pascal
« Reply #14 on: April 14, 2020, 03:48:42 pm »
"F" was a convention introduced I think by Borland. Perhaps it originally stood for "field"?
Whatever its origin, it has become a widely adopted convention that is a useful signal to people reading your code that you are referring to a private variable in the class.

 

TinyPortal © 2005-2018