C# Ütközés feladat:lista,linq,tömb rendezési algoritmusok nélkül.
2021-11-14T20:39:21+01:00
2021-11-21T18:28:02+01:00
2022-08-12T05:45:30+02:00
SmurkiG
Ütközés
Egy játéktáblán a 0. időegységben L bábu van. Mindegyiket elindítjuk valamerre. Egy 
időegység alatt mindegyik a neki megfelelő távolságra mozdul el, a tábla szélére érve 
megállnak. Lehetséges, hogy előbb-utóbb két bábu összeütközik: ugyanarra a helyre lépnének 
vagy átlépnének egymáson.
Készítsen programot, amely megadja, hogy K időegységen belül mikor ütközik legelőször 
két bábu!
A tabla.be szöveges állomány első sorában a játéktábla sorai és oszlopai száma 
(1<=N,M<=100), a bábuk száma (1<=L<=10) és az időtartam (1<=K<=100 000) van, egyetlen 
szóközzel elválasztva. A következő L sor egy-egy bábu leírását tartalmazza: a kezdő helyét 
(1<=Si<=N, 1<=Oi<=M) és mozgás irányát (Xi
,eleme:{F,L,J,B} – fel, le, jobbra, balra), egy-egy 
szóközzel elválasztva.
A tabla.ki szöveges állomány egyetlen sorába az első ütközés időpontját kell írni! Ha 
K időegységen belül nincs ütközés, akkor -1-et kell kiírni!
Példa:
tabla.be tabla.ki
7 10 3 100 3
4 3 J
2 6 F
4 8 B
Magyarázat: A bábuk helyzete időegységenként:
1: (4,4), (1,6), (4,7)
2: (4,5), (1,6), (4,6)
3: (4,6), (1,6), (4,5)
A 3. időegységre az 1-es és a 3-as bábu egymáson átlépett volna, azaz a 3. 
időegységben ütköztek


Lista,linq,illetve tömb rendezési algoritmusok nélkül kéne ezt a feladatot megoldanom.Köszönöm előre is a segítséget.
Mutasd a teljes hozzászólást!

  • Hát, ez a példa inputra működik. A fájlba írást és olvasást gondolom, már meg tudod oldani.

    Biztos, lehet rajta optimalizálni, de hirtelen örültem, hogy ezt így "papíron programozva" (a példa inputra) hiba nélkül össze tudtam hozni.

    using System; public record Board (int Rows, int Cols, (int, int, int, int)[] Figures, int CurrentTime, int MaxTimes, bool Collosion) { public static Board CreateFromFile(string fileContents) { int boardRows = 0; int boardCols = 0; (int, int, int, int)[] figures = null; int time = 0; string[] lines = fileContents.Split(Environment.NewLine); string[] boardData = lines[0].Split(' '); boardRows = Convert.ToInt32(boardData[0]); boardCols = Convert.ToInt32(boardData[1]); time = Convert.ToInt32(boardData[3]); figures = new (int, int, int, int)[Convert.ToInt32(boardData[2])]; for (int i = 0; i < figures.Length; i++) { string[] figureData = lines[i+1].Split(' '); int rowVector = figureData[2] switch { "F" => +1, "L" => -1, _ => 0 }; int colVector = figureData[2] switch { "J" => +1, "B" => -1, _ => 0 }; figures[i] = ( Convert.ToInt32(figureData[0]), Convert.ToInt32(figureData[1]), rowVector, colVector ); } return new Board(boardRows, boardCols, figures, 1, time, false); } public Board NextTurn() { (int Row, int Col, int RowVector, int ColVector)[] newPositions = ((int, int, int, int)[]) Figures.Clone(); for (int i = 0; i < newPositions.Length; i++) { int newRow = newPositions[i].Row + newPositions[i].RowVector; int newCol = newPositions[i].Col += newPositions[i].ColVector; bool isRowVectorApplicable = newRow >= 1 && newRow <= Rows; bool isColVectorApplicable = newCol >= 1 && newCol <= Cols; if (isRowVectorApplicable && isColVectorApplicable) { newPositions[i].Row = newRow; newPositions[i].Col = newCol; } } return this with { CurrentTime = CurrentTime + 1, Figures = newPositions, Collosion = CheckCollosion(newPositions) }; } private bool CheckCollosion((int Row, int Col, int RowVector, int ColVector)[] newPositions) { for (int i = 0; i < newPositions.Length; i++) { for (int j = i+1; j < newPositions.Length; j++) { if (i == j) continue; (int, int) FigureAOldPos = (Figures[i].Item1, Figures[i].Item2); (int, int) FigureBOldPos = (Figures[j].Item1, Figures[j].Item2); (int, int) FigureANewPos = (newPositions[i].Row, newPositions[i].Col); (int, int) FigureBNewPos = (newPositions[j].Row, newPositions[j].Col); bool isStepOver = FigureAOldPos == FigureBNewPos && FigureBOldPos == FigureANewPos; bool isSamePosition = FigureANewPos == FigureBNewPos; if (isStepOver || isSamePosition) return true; } } return false; } } public class Program { static readonly string input = @"7 10 3 100 4 3 J 2 6 F 4 8 B"; public static void Main() { Board b = Board.CreateFromFile(input); while (b.CurrentTime < b.MaxTimes && !b.Collosion) b = b.NextTurn(); if (b.Collosion) Console.WriteLine(b.CurrentTime); else Console.WriteLine(-1); } }
    Mutasd a teljes hozzászólást!
  • Váó köszönöm szépen a gyors segítséget.Végig olvasva kicsit méginkább összezavart bennem mindent(eléggé kezdő vagyok programozás téren és a logikát szeretném elsajátítani illetve fejlődni)
    Mutasd a teljes hozzászólást!
  • A C# 9-es verzióját használtam, így elég új lehet ez a szintaxis.

    A feladat megoldásához így gondolkodtam:
    Igazából a programunk kis világa 3 entitásból áll (játéktörténet, tábla, bábú).
    A bábunak van egy kezdőpozíciója (Row, Col), illetve egy mozgási vektora:
    J = (0, 1)
    B = (0, -1)
    F = (1, 0)
    L = (-1, 0)

    A tábláról tudni kell a méretét (Rows, Cols) és a rajta álló bábukat azoknak az adataival. Fontos fogalom a lépés, aminél arra kell figyelni, hogyha a bábu a tábla valamely szélén áll, és a mozgási vektora kivezetné őt a tábláról, akkor nem léphet a bábu.

    A játékmenetet én összemostam a táblával, de itt ami plusz információ az az, hogy melyik körben vagyunk most, hány körös maximum a játék, és volt-e ütközés.

    Az ütközésnél tudnunk kell összehasonlítani a tábla jelenlegi állapotát a következő körével. Ütközésről akkor beszélünk a feladat szerint, ha két bábu egymással helyet cserél (átlépnek egymáson), vagy a következő körre ugyanabba a mezőre lépnének.
    Mutasd a teljes hozzászólást!
  • Ahogy leírtad kezd azért tisztulni,arra megkérhetnélek esetleg ha időd engedi egy teljes értékű megoldást is letudnál írni ?Ezt a feladatot egy példagyűjteményben találtam ahol pszeudokóddal vannak maximum megadva a válaszok.Mivel kezdő vagyok ezért szeretném a feladatot megoldani tömbök,mátrixok illetve egyszerű és összetett programozási tételek és az OOP segítségével hogy alapszintű dolgokkal tudjak megoldani egy ilyen példát es hasonlókat.Nagyon köszönöm a válaszaidat sokat segítenek már a megértésben is.
    Mutasd a teljes hozzászólást!
  • Amikor kiírtad a kérdésedet, azt hittem, hogy
    1) A feladatot úgy, ahogy van, nem érted
    2) Téged abszolút nem érdekel a programozás, csak vagy a középiskolában, vagy az egyetemen van ilyen tantárgyad - ami bár kötelező valamiért, de azért jó lenne belőle nem megbukni.

    Most ezzel a válaszoddal tisztázódott, hogy érdekel téged a programozás világa, csak épp nem teljesen tudod megoldani egyedül ezt a feladatot. És ezzel nincs is semmi baj, azért tanulunk, hogy jobban menjen a programozás. És ehhez két terület fejlesztése vezet:
    1) A programozási nyelvre tekints úgy, mint egy eszköztárra - eszközöket ad a kezedbe ahhoz, hogy megoldj vele egy problémát. Tehát tudnod kell, hogy a nyelv milyen eszközöket kínál és azokat hogyan kell használni.
    2) Meg kell tanulni a számítógép agyával gondolkodni.

    Azt gondolom, hogy a te módszered, amit követsz, nem szolgálja az érdekeidet ahhoz, hogy megtanulj programozni. Ha kész megoldást kapsz, azzal nem fejlődnek úgy a képességeid, mintha órákon át próbálnád a problémát megoldani saját magadtól, elgondolkozva azon, hogy miért nem működik, aztán egyszercsak egy zuhanyzás közben rájönni, hogy "óh, hát ez a baj". Amit így tanulsz meg, az örökké a tiéd lesz.

    Ezért is nem javaslom azt, hogy tőlem várd a megoldást. Adtam egyet, mert azt hittem, hogy csak túl akarsz lenni rajta, de így, hogy tanulni akarsz, azt javaslom, hogy állj neki saját magad. Aztán ha elakadsz egy részletben, mert mondjuk nem tudod, hogy a kódodban miért nem működik mondjuk az ütközésvizsgálat, várunk szeretettel vissza itt a fórumon ^^

    Hajrá és sok sikert ^^
    Mutasd a teljes hozzászólást!
  • Hali!

    A jövőben mutasd – C#-forráskóddal/-részlettel –, hogy eddig mivel, hogyan próbálkoztál, meddig jutottál el, mi nem megy, miben/hol akadtál el!

    Mutasd a teljes hozzászólást!
  • Először is elnézést hogy 1 hét után jelentkezek újra csak másból is kellett készülnöm most,illetve igyeztem bővíteni a tudásomat(Fájl-Időkezelést megérteni).A feladatot OOP ismeretek miatt úgy kezdtem hogy osztályok hoztam létre(Bábu,Fájlkezelés céljából).A feladat bemeneti fájlját is hozzáadtam és ezután switch case-el az irányokat is megtudtam adni(vagyis remélem hogy jó).Segítségként kaptam azt hogy egy csináljak egy összehasonlitást ami egy új Bábu tömb lenne.Itt akadtam el.Ezért szeretném kéérni a további segítségeteket.Csatolnám az eddigi forráskodomat ide és előre is elnézést kérek ha esetleg túl sablonos lenne egyenlőre az oktató videók alapján csinálom mindegyik feladatom és így a tanár programozási stílusát követem.


    using System;
    using System.IO;
     
    namespace BabuFeladat
    {
        class Babu
        {
            public int BabuX;
            public int BabuY;
            public string MozgasiIrany;
     
            TablaFajl BabuFajl;
     
            public Babu(int X,int Y,string iranyuk,string tablafajl)
            {
                this.BabuX = X;
                this.BabuY = Y;
                this.MozgasiIrany = iranyuk;
                this.BabuFajl = new TablaFajl(tablafajl);
     
            }
     
            public void LepesekFajtai()
            {
                switch (MozgasiIrany)
                {
                    case "F":
                        {
                            if (BabuY == 0)
                            {
                                ;
                            }
                            else
                            {
                                BabuX--;
                            }
                            break;
     
                        }
     
                    case "L":
                        {
                            if (BabuY ==BabuFajl.TablaOszlopa)
                            {
                                ;
                            }
                            else
                            {
                                BabuX++;
                            }
                            break;
     
                        }
     
                    case "J":
                        {
                            if (BabuY == BabuFajl.TablaOszlopa)
                            {
                                ;
                            }
                            else
                            {
                                BabuY++;
                            }
                            break;
     
                        }
     
                    case "B":
                        {
                            if (BabuY == 0)
                            {
                                ;
                            }
                            else
                            {
                                BabuY--;
                            }
                            break;
     
                        }
     
                    default:
                        break;
                }
            }
     
        }
     
        class TablaFajl
        {
            public int TablaSora;
            public int TablaOszlopa;
            public int BabukSzama;
            public int FutasIdo;
                 
            public TablaFajl(string tablafajl)
            {
                StreamReader sr = new StreamReader("tabla.be.txt");
                string sor1 = sr.ReadLine();
                string[] darabolas = sor1.Split(' ');
     
                TablaSora = int.Parse(darabolas[0]);
                TablaOszlopa = int.Parse(darabolas[1]);
                BabukSzama = int.Parse(darabolas[2]);
                FutasIdo = int.Parse(darabolas[3]);
    Mutasd a teljes hozzászólást!
  • Pár javaslat:
    1) Szokj hozzá az angol elnevezésekhez. Bizonyára nem a semmiért tanulsz programozni, hanem terveid is vannak vele, így jó, ha már az elején hozzászoksz ahhoz, hogy a szakma nyelve az angol.
    2) Használj egységes elnevezési rendszert. Például itt:

    public Babu(int X,int Y,string iranyuk,string tablafajl)
    döntsd el, hogy a kódodban a paramétereket kis kezdőbetűvel kezded-e, vagy naggyal. Nem jó az, ha kevered, mert félreértésekhez vezethet. A C#-nak erre van hivatalos ajánlása, érdemes azt követned:
    Identifier names
    C# Coding Conventions

    3) Figyelj oda az elnevezésekre - például arra, hogy a metódus nevének valamilyen igét mindenképp tartalmaznia kell, mivel a metódusok valamilyen cselekvést írnak le. Ráadásul ez a metódusnév:

    public void LepesekFajtai()
    iszonyatosan félrevezető. Amit valójában csinál, az az, hogy elmozdítja a bábut abba az irányba, amely felé halad - tehát egy jobb név lenne az, hogy "Léptet()". A "LepesekFajtai()" névből a fejlesztők 100%-a arra következtetne, hogy megadja a bábuk lépéseinek lehetséges fajtáit, ami nagyon nem egyezik meg azzal, amit valójában csinál.

    Nem tudom, mennyire figyelted meg az én kódomat, de ha az egyik körből egy másik körbe léptem, én másolatot készítettem a körről (beleértve a táblát és a bábukat). Ez nagyon fontos, mivel a C# osztály reference-type, tehát egy ilyen problémába nagyon könnyen bele lehet szaladni:

    using System; class Figure { public int XPos { get; private set; } public int YPos { get; private set; } public int XVect { get; private set; } public int YVect { get; private set; } public Figure (int x, int y, int xvect, int yvect) { XPos = x; YPos = y; XVect = xvect; YVect = yvect; } public void Step() { XPos += XVect; YPos += YVect; } } record Board(Figure Figure); public class Program { public static void Main() { Figure f = new Figure(5, 3, 1, 1); Board a = new Board(f); f.Step(); Board b = new Board(f); Console.WriteLine($"{a.Figure.XPos}, {a.Figure.YPos}"); Console.WriteLine($"{b.Figure.XPos}, {b.Figure.YPos}"); } }
    Mutasd a teljes hozzászólást!
  • Köszönöm szépen a tanácsokat mindenképpen megfogadom őket.A gyakorló videókat amiket nézek abban ugye magyarul vannak megadva a változó nevek,metódusok stb.Természetesen néztem a te kódodat csak azt még nem igazán tudom érteni.Ezeket a dolgokat leszámítva jó a gondolkodás módom a feladattal kapcsolatban?Azóta még tudtam haladni egy kicsit(vagyis remélem hogy haladtam és nem csak rontottam a dolgon)
    Mutasd a teljes hozzászólást!
abcd