Archief - Tabel maken in Java console

Het archief is een bevroren moment uit een vorige versie van dit forum, met andere regels en andere bazen. Deze posts weerspiegelen op geen enkele manier onze huidige ideeën, waarden of wereldbeelden en zijn op sommige plaatsen gecensureerd wegens ontoelaatbaar. Veel zijn in een andere tijdsgeest gemaakt, al dan niet ironisch - zoals in het ironische subforum Off-Topic - en zouden op dit moment niet meer gepost (mogen) worden. Toch bieden we dit archief nog graag aan als informatiedatabank en naslagwerk. Lees er hier meer over of start een gesprek met anderen.

cosmo2

Legacy Member
Ik moet voor een project een tabel maken met gegevens, maar ik zou niet weten hoe er aan te beginnen. Ik heb gegoogled en ben op dit uitgekomen. Maar ik wil een tabel waar alles mooi verdeeld is. Dit is hoe hij er moet uitzien: voorbeeld. En als het met System.out.printf moet, zoals op die site, kan er dan soms iemand de parameters uitleggen?

Alvast bedankt.

cosmo2

Legacy Member
Ik heb geprobeerd, maar nu moet ik altijd de lengte instellen van de parameters van printf als mijn getal korter wordt in lengte...

Code:
+--------+------------+------------+------------+------------+
| MAAND  |    SALDO   | KAPAFLOSS  |   INTREST  |  AFLOSSING |
+--------+------------+------------+------------+------------+
|   0    |    10000.00   |   |             |   |
|   1    |    9833.33   |   |             |   |
|   2    |    9666.67   |   |             |   |
|   3    |    9500.00   |   |             |   |
.....
|   54   |    1000.00   |   |             |   |
|   55   |    833.33   |   |             |   |
|   56   |    666.67   |   |             |   |
|   57   |    500.00   |   |             |   |
|   58   |    333.33   |   |             |   |
|   59   |    166.67   |   |             |   |
|   60   |    0.00   |   |             |   |

In de eerste kolom is dit geen probleem omdat mijn getallen maar tot 60 moeten gaan en dus een maximum lengte van 2 digits hebben, maar in de 2e kolom geeft dit een probleem omdat het start getal varieert naargelang de input van de gebruiker.

Dus bij deze zoek ik nog altijd een oplossing.

metalleke

Legacy Member
Je kunt normaal zowel links als rechts uitlijnen. Toon es wat je al hebt van code.

cosmo2

Legacy Member
Dit is de code die bovenstaande tabel genereert:

Code:
 public void aflVastKap(){
        for (int i = 1; i <= compleetT1.length; i++){
            if (i == 1 | i == 10 | i == 23 | i == 36 | i == 49){
                System.out.print("+");
            }
            else if (i == 62){
                 System.out.print("+");
                 System.out.println();
                 System.out.printf("%8s %8s %8s %8s %8s\n", "| MAAND  |", "   SALDO  ", "| KAPAFLOSS  |", "  INTREST ", "|  AFLOSSING |");
            }
            else{
                System.out.print("-");
            }
        }
        for (int j = 1; j <= compleetT1.length; j++){
            if (j == 1 | j == 10 | j == 23 | j == 36 | j == 49 | j == 62){
                System.out.print("+");
            }
            else{
                System.out.print("-");
            }
        }
        System.out.println();
        for (int x = 0; x < compleetT1.length; x++){
             if (x > 10){
                System.out.printf("%6s %8s %2s %8s %8s\n", "|   " + x + "   |", "   " + frmt2.format(compleetT1[x]) + "  ", "| " + "  |", "  " + " ", "| " + "  |");
             }
             
             else if (x < 10){
                System.out.printf("%6s %8s %2s %8s %8s\n", "|   " + x + "    |", "   " + frmt2.format(compleetT1[x]) + "  ", "| " +  "  |", "  " + " ", "| " + "  |");
             }
        }
       
        
    }

Zoals je op het einde kan zien, moest ik de getallen onder 10 en boven 9 opnieuw ordenen zodat zo mooi in het midden staan.
compleetT1[] is de array waarin de "saldo" bedragen in opgeslaan staan.

Raanº³

Legacy Member
Waarom maak je de tabelheaders "statisch" ?

Kun je niet beter ze in een string variabele steken, een functie maken a la "int getMaxLengteArray(const float[](of w/e type) & compleetT1, const string & header)" en een functie van "getLengteArrayItem(const float & kapitaal)". De string header heb je nodig voor in het geval je header dus groter is in lengte dan de gegevens in je array, zodat de headers goed blijven. & staat voor reference variable in C++, dus ik denk dat dit gewoon 'ref' is in java?

Dan kun je bijvoorbeeld met de uitlijning manueel spelen door bvb eerst de maximale lengte op te vragen en aangezien je de uitlijning rechts hebt in de voorbeeld, hoef je maar spaties toe te voegen met een loop.

Iets op het gedacht van:
Eerst de maximale lengte uit je array halen, die dan gebruiken om je headers dynamischer te maken. Bij de uitlijning van je headers kun je dan maximum lengte \ 2 (A) doen, je string ook \ 2 (B) en dan kun je eerst een loop doen van spaties tot (A-B) om dan je string te outputten.

Daarna weer een loop om de resterende spaties er te krijgen. Dan kun je ook gemakkelijker de plusjes en de verticale bars er aan toe voegen in plaats van ze statisch te plaatsen.

Dan kun je de "content" van de tabel ook gemakkelijker invullen. Door je "algemene functies" kun je de functies voor elke rij & kolom van de tabel gebruiken en die zo dynamisch aanpakken.

Geen idee of je hier iets mee bent, aangezien ik waarschijnlijk je oefening redelijk wat ingewikkelder heb gemaakt :D

Trouwens, let ook op in je voorbeeld: je gebruikt de bit operator |, in wat ik zie wil je || (logische OF). Wat je nog gemakkelijker kunt doen is dus het in een switch steken en die laat trapvallen

Code:
string test = "";
	
switch(int value)
{
           case 1:
			test += "1\n";
	   case 10:
			test += "10\n";
			break;
	   case 2:
			test += "2\n";
			break;
           case 22:
           case 23:
                        test += "Te lui om 22 of 23 apart te schrijven";
                        break;
	   case 4:
			test += "4\n";
	   default:
	           test += "Geen van bovenstaande waarden";
			   break;
}
--> indien value 4 zou zijn, krijg je "4 [enter] Geen van bovenstaande waarden" in de string, omdat je het laat doorvallen.
--> indien value 2, krijg je "2" in de string
--> indien value 1, krijg je "1 [enter] 10" in de string
--> indien value 10, krijg je "10" in de string
--> indien value 255, krijg je "Geen van bovenstaande waarden" in de string
--> indien value 23 (of 22), krijg je "Te lui om 22 of 23 apart te schrijven" in de string

cosmo2

Legacy Member
De tabelheaders zijn statisch omdat die nooit hoeven te veranderen. Er blijft altijd MAAND, SALDO, KAPAFLOSS, etc... in staan. Die veranderen nooit van lengte. Kzal straks je post eens deftig lezen, want moet nu gaan werken.

EDIT:
Ik snap wat je bedoelt, maar ik denk dat het nogal moeilijk gaat zijn om dit toe te passen :p
Ik moet ook volgens de richtlijnen van het project, max 15 - 20 regels / methode hebben en ik zit nu al aan exact 20 voor juist de header en de 5 kolommen...en dan moet ik nog een footer ook maken, dus er moet een simpelere manier zijn.

Raanº³

Legacy Member
cosmo2 zei:
Ik moet ook volgens de richtlijnen van het project, max 15 - 20 regels / methode hebben
Dit los je vrij simpel op door functie(s) in functie(s) te steken.

Code is in C++ geschreven, zou niet lang mogen duren voordat je deze logica in Java kunt omzetten; cout is equivalent van System.out.print
Code:
string printBorder()
{
        return "+-----+\n";
}
string printHeaderNames()
{
        return "| ID  |\n";
}

string printHeader()
{
        string header = "";

        header += printBorder();
        header += printHeaderNames();
        header += printBorder();

        return header;
}

int main()
{
        string header = printHeader();

        cout << header;
        return 0;
}
Output zal dan zijn:
Code:
+-----+
| ID  |
+-----+

Natuurlijk zou in dit simpel voorbeeld het redelijk overbodig zijn om het zo aan te pakken, aangezien je maar 1 regel code in je functies hebt, maar eens je meerdere regels code hebt, is het (o.a.) veel overzichtelijker om het zo te doen. De logica van max. 20 regels per functie is eigelijk om bugs te vermijden en "logisch" gezien zou een functie maar 1 ding mogen uitvoeren. Daarom dien je functies in functies op te roepen.

In dit voorbeeld doet printHeader() een logische actie, namelijk je header outputten. Om een Header te outputten, moet je een border outputten en de Header zelf. printBorder() zou je in principe nog eens kunnen onderverdelen in printBorderBoundaries (welke je 2x oproept, in het begin & eind, en een '+' retourneert, en dan printBorderSpace(int <A>, char <B>) voor de (lengte -2)<A> van je kolombreedte en je token zelf<b> en dit zou je nog eens kunnen een functie kunnen gebruiken voor printBorderSpaceToken(char <B>) welke je 'token B' retourneert. ) headerNames zou je in principe ook met een parameter moeten werken (string[] oid) waarbij je dan een foreach doet etc etc...

Geen idee of dit een werkproject is of uit jezelf maar let vooral op bij magische constanten (dit zijn constanten die je 'hardcoded' erin steekt zoals bvb je i==10 op regel 3 van je voorbeeld -- er is geen 'logische' verklaring waarom i 10 moet zijn om een plusje te schrijven). Ideaal gezien gebruik je geen 'magie' in je applicatie, maar onderbouw je alles door middel van logica ;-)

Misschien kun je ook eens kijken om Object Georienteerd te werken ipv procedural. En bekijk ook eens dan informatie over Multi-Layered applicaties, de output is dus de laatste laag (Presentation layer logic); Anders kun je het best proberen met namespaces om het toch nog iets wat logisch in te kunnen delen. Zo zou je principeel gezien een namespace Border hebben, en daarin dan je functies om je Border te 'formatten' e.d.

cosmo2

Legacy Member
Helaas is dit inderdaad een schoolproject en kunnen er dus geen uitzonderingen gemaakt worden én mag het niet in OO gedaan worden, dat is mijn 2e project. Maar beginnen bij begin hé. Wat ik versta uit je code is eigenlijk hetzelfde als dit:

Code:
System.out.println("+--------+------------+------------+------------+------------+");
        System.out.println("| MAAND  |    SALDO   |  KAPAFLOSS |   INTREST  | AFLOSSING  |");
        System.out.println("+--------+------------+------------+------------+------------+");

Maar dan de 3 lijnen in een verschillende methode?

Dit zou dan hetzelfde zijn als:

Code:
]System.out.println("+--------+------------+------------+------------+------------+\n"| MAAND  |    SALDO   |  KAPAFLOSS |   INTREST  | AFLOSSING  |\n+--------+------------+------------+------------+------------+");

Dit is misschien een goede methode voor de header, maar niet echt voor de gegevens. Misschien heb je het wel uitgelegd hoe het dan moet met gegevens, maar zal erover gelezen hebben :p

Raanº³

Legacy Member
Je hebt er inderdaad overgelezen. Normaal gezien zou je met je eigen kennis en met mijn voorgaande 2 posts deze oefening perfect moeten kunnen maken.

Je hebt hoogst waarschijnlijk wel al geleerd hoe gegevens - algemeen gezien - dienen verwerkt te worden: invoer, verwerking en uitvoer.

Invoer staat voor alles wat de gebruiker dient in te putten; in dit geval zal dit het beginsaldo (in EUR), intrestvoet en of maandelijkse kapitaalaflossing (in EUR) of termijn (in maanden) zijn.

Verwerking (Business Logic Layer) staat voor de berekening van de maandelijkse intrest, totale aflossing, en afhankelijk van de applicatie de kapitaalaflossing.

Ideaal gezien werk je met een 2 dimensionale array: resultaat[t][n], waarvoor [t] staat voor de rij, en [n] staat voor de kolom. Wil je de aflossing weten voor de 10de maand (bijvoorbeeld), dan zou je in dit geval resultaat[10][3] kunnen opvragen. Indexen beginnen vanaf 0, dus [3] = 4de kolom. Een maand hoef je niet in de array op te slaan, aangezien deze in dit geval gelijk is aan je index.

Voor de rij index kun je ofwel [0] = 1° maand gebruiken of je gebruikt de [1] index om de eerste maand weer te geven. Dan zou je eventueel de [0] (ongebruikte) index kunnen gebruiken om essentiele gegevens van je array bij te houden (zoals bijvoorbeeld de maximum lengte van de waarden uit die kolom).

Dan kun je met een loop alle gegevens in je array invullen.

Uitvoer (Presentation Logic Layer) staat in dit geval voor het tonen van je (ingevulde) tabel. Tegen dat je hier bent, heb je alle gegevens zowiezo al verwerkt.

Dit projectje is niet zo moeilijk, maar leert je wel om orderlijk & gestructureerd te werken. Alsook kan je mogelijk tegen problemen/limitaties stuiken die later deftiger zullen behandeld worden.

Let ook op dat je geen copy/paste manieren toepast.

Als je bijvoorbeeld volgende code tegenkomt:
PHP:
for (int i = 0; i < resultaat.length; i++)
{
    for (int j = 0; j < resultaat[0].length; j++)
    {
		if (j == 1)
			resultaat[i][j] = berekenKapitaalAflossing(resultaat[i][0]);
		if (j == 2)
			resultaat[i][j] = berekenIntrest(resultaat[i][0]);
		if (j == 3)		
			resultaat[i][j] = berekenAflossing(resultaat[i][0]);
    }
}
kun je beter eens kijken of je dit niet slimmer kunt oplossen ipv steeds dezelfde parameter mee te moeten geven. Een oplossing zou zijn om bijvoorbeeld een functie te maken die je saldo als parameter meekrijgt en die een array met de berekende waarden retourneert.
PHP:
float[] bereken(float Saldo)
{
	float[] resultaat = new float[3];
	
	resultaat[0] = berekenKapitaalAflossing(Saldo);
	resultaat[1] = berekenIntrest(Saldo);
	resultaat[2] = berekenAflossing(Saldo);
	
	return resultaat;
}

for (int i = 0; i < resultaat.length; i++)
{
	float[] resultRij = bereken(resultaat[i][0]);

	// KapAflossing
	compleetT1[i][1] = resultRij[0];
	// Intrest
	compleetT1[i][2] = resultRij[1]
	// Aflossing
	compleetT1[i][3] = resultRij[2];
    }
}

etc etc

@blackrabbit: In weze maakt het niet echt uit in welke taal het geschreven dient te worden. De logica blijft steeds dezelfde, gelijk in welke programmeertaal je ook wenst te programmeren. Heb je de logica/ gebruik van arrays/... niet door, dan zul je zelfs in een simpele taal als VB.NET sukkelen.

blackrabbit

Legacy Member
Raanº³ zei:
@blackrabbit: In weze maakt het niet echt uit in welke taal het geschreven dient te worden. De logica blijft steeds dezelfde, gelijk in welke programmeertaal je ook wenst te programmeren. Heb je de logica/ gebruik van arrays/... niet door, dan zul je zelfs in een simpele taal als VB.NET sukkelen.
Euhm, ok.

't Gaat er mij vooral om dat het niet in OO mag geschreven worden, maar dat hij wel in Java bezig is. Waarom dan niet werken met een procedurele/functionele/declaratieve/... taal?

cosmo2

Legacy Member
Bedankt Raan voor je gigantische hulp.
Heb het eindelijk voor mekaar gekregen en tziet der prachtig uit :)

Voor moest iemand er naar zoeken en in deze thread komen.
Hier is wat ik gedaan heb:

Code:
    public String uitlijning (String getal){
        switch(getal.length()){
            case 9:
                return getal + " ";
            case 8:
                return getal + "  ";
            case 7:
                return getal + "   ";
            case 6:
                return getal + "    ";
            case 5:
                return getal + "     ";
            case 4:
                return getal + "      ";
            case 3:
                return getal + "       ";    
            case 2:
                return getal + "        ";
            case 1:
                return getal + "         ";
        }
        
        return getal;
    }

En dan gewoon in je tabel

Code:
uitlijning(String)

zetten en voila :)
Het archief is een bevroren moment uit een vorige versie van dit forum, met andere regels en andere bazen. Deze posts weerspiegelen op geen enkele manier onze huidige ideeën, waarden of wereldbeelden en zijn op sommige plaatsen gecensureerd wegens ontoelaatbaar. Veel zijn in een andere tijdsgeest gemaakt, al dan niet ironisch - zoals in het ironische subforum Off-Topic - en zouden op dit moment niet meer gepost (mogen) worden. Toch bieden we dit archief nog graag aan als informatiedatabank en naslagwerk. Lees er hier meer over of start een gesprek met anderen.
Terug
Bovenaan