Középiskolai Matematikai és Fizikai Lapok
Informatika rovattal
Kiadja a MATFUND Alapítvány
Már regisztráltál?
Új vendég vagy?

A 2001. októberi informatika feladatok megoldása

A közöltek csak megoldásvázlatok, esetleg csak végeredmények. A maximális pontszám eléréséhez általában ennél részletesebb megoldás szükséges. A részletes megoldásokat a beküldött dolgozatok alapján a KöMaL-ban folyamatosan közöljük.


I. 4. ,,Nagyon'' prímeknek nevezzük az olyan prímszámokat, amelyek bármely kezdőszelete is prímszám. Például nagyon prím a 239, mert a 2, a 23 és a 239 is prím; nem nagyon prím a 241, ami ugyan prímszám, a 2 is prím, de a 24 nem az. Készíts programot, amely előállítja az összes N jegyű nagyon prímet (1leNle8)! A program írja ki ezen számok kezdőszeleteit is! A helyes megoldások közül az ér többet, amelyik rövidebb idő alatt fut le. Példa (n=3 esetén): 2, 23, 233      2, 23, 239       2, 29, 293      3, 31, 311 (10 pont)

A megoldás tartalmazza a feladat értelmezését, azaz a specifikációt, illetve az algoritmust.

A bemenő adat N, mely megmondja, hogy hány jegyű nagyon prímekre és azok kezdőszeleteire vagyunk kíváncsiak.

Pascal program:



Program Nagyon_primek;
  uses newdelay,crt;
  var i,j,n: longint;
      f: text;

  Function prim_e(i: longint): Boolean;
    var j: longint;
  begin
    j:=2; while (j*j<=i) and (i mod j>0) do j:=j+1;
    prim_e:=j*j>i;
  end;

  Procedure kiiras(i: longint);
    var j: longint;
  begin
    if i<10 then write(f,i:5)
            else begin kiiras(i div 10); write(f,', ',i:5); end;
  end;

  Procedure n_jegyuek(p,i,n: longint);
    var j,h: longint;
  begin
    if i=n then
    begin
      kiiras(p); writeln(f);
    end
      else
    begin
      j:=1;
      while j<=9 do
      begin
        h:=10*p+j;
        if prim_e(h) then n_jegyuek(h,i+1,n);
        j:=j+2;
      end;
    end;
  end;

begin
  clrscr;
  repeat
    write('Hány jegyűek?'); readln(n);
  until n>0;}
  assign(f,'prim.out');
  rewrite(f);
  for n:=1 to 8 do
  begin
    n_jegyuek(2,1,n); n_jegyuek(3,1,n); n_jegyuek(5,1,n); n_jegyuek(7,1,n);
    writeln(f);
  end;
  close(f);
  repeat until keypressed;
end.


I. 5. Készítsünk programot, amely egy egységkockát ábrázol a képernyőn drótvázas és takart vonalas ábrázolásban! A kocka középpontja az origóban legyen, és a z tengely irányából adott távolságról nézzük. A program a kockát tetszőleges koordináta tengely körül tudja forgatni! (10 pont)

A megoldás egyszerűsített forrásértelmezése:

Pascal program:



Program Okt2;
  Uses
    newdelay,Crt,Graph;
  Type
    vektor=Record
      x,y,z:Real;
    End;{_Record}
    TMatrix=Array[1..4,1..4] Of Real;
    TVektor=Array[1..4] Of Real;
  Const  {_Kezdoertekkel rendelkezo valtozo}
    kocka:Array[0..7] Of vektor=((x:-0.5;y:-0.5;z:0.5),(x:0.5;y:-0.5;z:0.5),(x:-0.5;y:-0.5;z:-0.5),(x:0.5;y:-0.5;z:-0.5),
                                (x:-0.5;y:0.5;z:0.5),(x:0.5;y:0.5;z:0.5),(x:-0.5;y:0.5;z:-0.5),(x:0.5;y:0.5;z:-0.5));
    lap:Array[1..6] Of vektor=((x:0;y:-1;z:0),(x:0;y:0;z:1),(x:-1;y:0;z:0),(x:1;y:0;z:0),(x:0;y:0;z:-1),(x:0;y:1;z:0));
    lapleiras:Array[1..6,1..4] Of Byte=((0,1,3,2),(0,1,5,4),(0,2,6,4),(1,3,7,5),(2,3,7,6),(4,5,7,6));
    path:STRING=''{'g:\munka\tp\bgi'};
    BOldalra=5;
    JOldalra=6;
    Balra=1;
    Jobbra=2;
    Fel=3;
    Le=4;
  Var
    oldallap:Array[1..4] Of PointType;
    vonalak:Boolean;
    Ch:Char;
    szog:Real;
  Procedure OpenGraph;
    Var
      gd,gm:Integer;
  Begin
    gd := Detect;
    InitGraph(gd,gm,path);
  End;{_OpenGraph}
  Procedure Rajzol;
    Var
      i:Byte;
    Function szin(r:Real):Word;
    Begin
      szin:=Trunc(15*r);
    End;
    Function toltes(j:Byte):Word;
    Begin
      If lap[j].x>0
        Then toltes:=BkSlashFill
        Else toltes:=SlashFill;
      If lap[j].y>0.5
        Then toltes:=SolidFill;
    End;
  Begin
    SetFillStyle(1,0);
    Bar(0,0,GetMaxX,GetMaxY);
    If vonalak
      Then Begin
        MoveTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[0].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[0].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[1].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[1].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[3].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[3].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[2].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[2].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[0].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[0].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[4].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[4].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[5].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[5].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[7].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[7].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[6].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[6].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[4].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[4].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[5].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[5].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[1].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[1].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[3].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[3].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[7].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[7].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[6].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[6].y));
        LineTo(GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[2].x),GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[2].y));
      End
      Else Begin
        For i:=1 To 6 Do Begin
          If lap[i].z>0
            Then Begin
              oldallap[1].x:=GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[lapleiras[i,1]].x);
              oldallap[1].y:=GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[lapleiras[i,1]].y);
              oldallap[2].x:=GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[lapleiras[i,2]].x);
              oldallap[2].y:=GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[lapleiras[i,2]].y);
              oldallap[3].x:=GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[lapleiras[i,3]].x);
              oldallap[3].y:=GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[lapleiras[i,3]].y);
              oldallap[4].x:=GetMaxX div 2 + Trunc((GetMaxY div 4)*kocka[lapleiras[i,4]].x);
              oldallap[4].y:=GetMaxY div 2 - Trunc((GetMaxY div 4)*kocka[lapleiras[i,4]].y);
              SetFillStyle(toltes(i), szin(lap[i].z));
              FillPoly(4,oldallap);
            End;
        End;{_For}
      End;
  End;{_Rajzol}
  Function Rad(b:Real):Real;
  Begin
    Rad:=b*Pi/180;
  End;{_Rad}
  Procedure Forgat(merre:Byte);
    Var
      A:TMatrix;
      v,v2:TVektor;
      i:Integer;
    Procedure MatrixVektorSzorzas(M:TMatrix;b:TVektor;Var k:TVektor);
      Var
        c:TVektor;
        j,l:Byte;
    Begin
      For j:=1 To 4 Do Begin
        c[j]:=0;
        For l:=1 To 4 Do
          c[j]:=c[j]+M[j,l]*b[l];
      End;{_For}
      For j:=1 To 4 Do
        k[j]:=c[j];
    End;{_MatrixVektorSzorzas}

    Procedure Forgatas;
    Begin
      MatrixVektorSzorzas(A,v,v2);
    End;{_Forgatas}

    Procedure MatrixMegadas;
    Begin
      Case merre Of
        BOldalra:Begin
                   A[1,1]:=cos(rad(szog));
                   A[1,2]:=0;
                   A[1,3]:=-sin(rad(szog));
                   A[2,1]:=0;
                   A[2,2]:=1;
                   A[2,3]:=0;
                   A[3,1]:=sin(rad(szog));
                   A[3,2]:=0;
                   A[3,3]:=cos(rad(szog));
                 End;{BOldalra}
        JOldalra:Begin
                   A[1,1]:=cos(rad(-szog));
                   A[1,2]:=0;
                   A[1,3]:=-sin(rad(-szog));
                   A[2,1]:=0;
                   A[2,2]:=1;
                   A[2,3]:=0;
                   A[3,1]:=sin(rad(-szog));
                   A[3,2]:=0;
                   A[3,3]:=cos(rad(-szog));
                 End;{JOldalra}
        Balra:Begin
                 A[1,1]:=cos(rad(-szog));
                 A[1,2]:=-sin(rad(-szog));
                 A[1,3]:=0;
                 A[2,1]:=sin(rad(-szog));
                 A[2,2]:=cos(rad(-szog));
                 A[2,3]:=0;
                 A[3,1]:=0;
                 A[3,2]:=0;
                 A[3,3]:=1;
              End;{_Balra}
        Jobbra:Begin
                A[1,1]:=cos(rad(szog));
                A[1,2]:=-sin(rad(szog));
                A[1,3]:=0;
                A[2,1]:=sin(rad(szog));
                A[2,2]:=cos(rad(szog));
                A[2,3]:=0;
                A[3,1]:=0;
                A[3,2]:=0;
                A[3,3]:=1;
               End;{_Jobbra}
        Fel:Begin
             A[1,1]:=1;
             A[1,2]:=0;
             A[1,3]:=0;
             A[2,1]:=0;
             A[2,2]:=cos(rad(-szog));
             A[2,3]:=-sin(rad(-szog));
             A[3,1]:=0;
             A[3,2]:=sin(rad(-szog));
             A[3,3]:=cos(rad(-szog));
            End;{_Fel}
        Le:Begin
              A[1,1]:=1;
              A[1,2]:=0;
              A[1,3]:=0;
              A[2,1]:=0;
              A[2,2]:=cos(rad(szog));
              A[2,3]:=-sin(rad(szog));
              A[3,1]:=0;
              A[3,2]:=sin(rad(szog));
              A[3,3]:=cos(rad(szog));
           End;{_Le}
      End;{_Case}
      A[1,4]:=0;
      A[2,4]:=0;
      A[3,4]:=0;
      A[4,1]:=0;
      A[4,2]:=0;
      A[4,3]:=0;
      A[4,4]:=1;
    End;{_MatrixMegadas}
  Begin
    MatrixMegadas;
    For i:=0 To 7 Do Begin
      v[1]:=kocka[i].x;
      v[2]:=kocka[i].y;
      v[3]:=kocka[i].z;
      v[4]:=1;
      Forgatas;
      kocka[i].x:=v2[1];
      kocka[i].y:=v2[2];
      kocka[i].z:=v2[3];
    End;
    For i:=1 To 6 Do Begin
      v[1]:=lap[i].x;
      v[2]:=lap[i].y;
      v[3]:=lap[i].z;
      v[4]:=1;
      Forgatas;
      lap[i].x:=v2[1];
      lap[i].y:=v2[2];
      lap[i].z:=v2[3];
    End;
  End;{_Forgat}
Begin
  ClrScr;
  OpenGraph;
  vonalak:=TRUE;
  szog:=10;
  SetColor(15);
  Repeat
    Rajzol;
    Ch:=ReadKey;
    If Ch=#0
      Then Ch:=ReadKey;
    Case Ch Of
      #75:Forgat(BOldalra);
      #77:Forgat(JOldalra);
      #72:Forgat(Fel);
      #80:Forgat(Le);
      #73:Forgat(Jobbra);
      #81:Forgat(Balra);
      #49,#79:If vonalak
                Then vonalak:=FALSE
                Else vonalak:=TRUE;
    End;{_Case}
  Until Ch=#27;
  CloseGraph;
End.


I. 6. A rugó rezgésének ,,szemléltetésére'' a következő a szimulációs modellt alkotjuk. Az ,,ideális'' (elhanyagolható tömegű) rugóra akasszunk óvatosan egy M tömegű testet, aminek hatására a rugó valamennyire megnyúlik, majd nyugalomban marad. Ezzel a tömeggel együtt L hosszúságúra nyújtjuk a rugót. Elengedve, a rugón a tömeg rezgőmozgásba kezd. Ezt a mozgást kell utánozni úgy, hogy kellő rövidségű időegységet választva (Deltat) kiszámítjuk az abban a pillanatban érvényes megnyúlást, eredő erőt (ami az M tömeg súlyából és a rugó megnyúlásától függő erőből tevődik össze), gyorsulást és sebességet. Írjunk Excel táblázatot (amelynek neve: RUGO.XLS) ennek a fizikai modellnek a vizsgálatára!

a) Adjuk meg az F (eredő erő), az a (gyorsulás), a v (sebesség) és az l (megnyúlás) alakulását az első 200 időegységben.

b) Ábrázoljuk grafikonon a megnyúlás változását!

c) A modell paraméterei (D rugóállandó, KE közegellenállási együttható, az L kezdeti megnyúlás, az M tömeg és a \(\displaystyle Delta\)t időintervallum) a táblázat bal felső sarkában legyenek találhatók (igény szerint módosíthatók).

d) Hogyan alakul a szimuláció, ha a közegellenállást is figyelembe vesszük? (10 pont)

A megoldás ez az Excel táblázat:

A B1-tól B5-ig található cellákba és a B8 cellába Valamilyen értéket kell megadnunk értelemszerűen. A többi adat már mind számolt.

B6 természetesen a B1 és B4 szorzata.

B7 az egyenes vonalú egyenletesen gyorsuló közelítés miatt egy előre kiszámolt konstans értéket tartalmaz. Mégpedig: t2/2.

A B9 cellába kiszámolásra kerül a nyugalmi szint úgy, hogy a rugóra akasztott test egyszerűen csak lóg. Vagyis a megnyúlás, ami ekkor a nyugalmi szint egyenlő lesz a súlyának és a rugó rugóállandójának hányadosával. x0=Mg/D=$B$6/$B$2

B11 a kezdő időpont, vagyis 0.

A 11. sorban szerepel a kezdettől eltelt idő úgy, hogy mindig az előző cella értékéhez hozzáadunk egyet, a dT-t.

B12 a kezdősebesség nulla, hiszen a megnyújtás után csak elengedjük a testet.

A 12. sorban szerepel a sebesség, mely az elengedés pillanatában nulla, majd periodikusan változik. Függ az előző sebességtől illetve az előző gyorsulástól. Itt azt a közelítést használjuk, hogy nagyon kis időintervallumokat véve feltételezzük az egyenletesen gyorsuló mozgást. v2=v1+at. Tehát például: D12=C12+C15*$B$3.

B13 a kezdeti kitérés az, amennyire megnyújtottuk a testet, azaz B5-tel megegyezik.

A 13 sorban tovább a kitérések található, melyeket az s2=s1+v1t+(a/2)t2 közelítéssel számolunk ki, vagyis például D13=C13+C12*$B$3+$B$7*C15

B14 a rugóerőnek az a része, ami csak a nyugalmi helyzettől való eltérésből származik, így ez kezdetben F=Dx , azaz B14=$B$2*B13.

A 14. sorban tovább az erő kiszámításánál a közegellenállásból származó erőt is figyelembe vesszük, hozzáadjuk az előbbi módon kiszámított erőhöz. Például D14=-$B$2*D13+D17

A 15. sor végig az adott időhöz tartozó gyorsulást mutatja. a=F/m, azaz például: B15=B14/$B$1.

A 16. sorban már a rugó nyugalmi helyzetéhez viszonyított pozíció szerepel. Vagyis a 13. sor van eltolva a nyugalmi szintre.

A 17. sorban a közegellenállásból származó erőt számoljuk ki, olyan közelítéssel, hogy ez az erő egyenesen arányos sebességgel. Például: F17=-F12*$B$8. Itt a negatív előjelre az erő iránya miatt van szükség.