# Zeilen/Spaltenzahl



## CEric (1. Mrz 2012)

Hi!
Ich will die Spaltenzahl meines mehrdim. array String[][]tabelle; bekommen. 
Mein Code:

```
public int getColumns() {
		
		int spalten = tabelle[0].length;

		for(int y = 0; y < tabelle[0].length; y++){
			for(int x = 0; x < tabelle.length; x++){
				if(tabelle[x][y] == ""){
					spalten = spalten - 1;
					return spalten;
					}
				else if(tabelle[x][y] != ""){
					return spalten;
				}
			}
		}
		return spalten;

	}
```
Enthält eine Spalte den leeren String "", dann gilt sie als nicht benutz und werden nicht mitgezählt!
Problem das ich jetzt habe ist, dass ich bei jedem Schleifendurchlauch für jede Zeile x, wo ein leerer String auftritt die Spaltenzahl reduziere, obwohl ich ja noch in der gleichen Spalte y bin!
Wie kann ich das verhindern?


----------



## nillehammer (1. Mrz 2012)

Hab den Code nicht bis ins letzte nachvollzogen, aber die return-Statements in der Schleife sind sicher nicht richtig. *Außerdem werden String-Vergleiche mit equals() gemacht!!!!!*


----------



## CEric (1. Mrz 2012)

Ok dann mit tabelle[x][y].equals(""), oder!
Nunja, ich hab das Array das ne Tabelle darstellen soll in dem Strings gespeichert sind, zB Namen!
Das ganze eben mit Zeilen x und Spalten y, jetzt soll ich die verwendeten Spalten ausgeben, enthält die Spalte einen leeren String, ist sie nicht verwendet und wird abgezogen!
Bei meinem code rduziere ich aber jetzt immer spalten - 1; 
wenn ich jetzt aber in Spalte 1 bin und Zeile 1 und dort ist ein leerer String, dann is das ja richtig!
hüpfe ich aber zu Zeile 2 in spalte 1 und da is auch ein leerer String,  dann mach ich ja wieder spalten - 1; was dann ja falsch ist!

kann das sein?

```
int y = 0;
			for(int x = 0; x < tabelle.length; x++){
				if(tabelle[x][y].equals("")){
					spalten = spalten - 1;
					y++;
					return spalten;
					}
```


----------



## nillehammer (1. Mrz 2012)

Sorry für mein Schreien. Ich hab die Schriftgröße inzwischen verkleinert. Aber ich hab diesen Satz in letzter Zeit zu oft geschrieben. Nicht deine Schuld.

Zerlege Dein Gesamtproblem am besten in Teilprobleme, welche Du in einzelnen Methoden abhandelst und benutze sprechende Namen (ok, kann sein, dass x und y für Dich sprechend sind. Ich finde zeile/spalte sprechender). Dann fällt es Dir leichter, die Lösung zu finden. Etwa so:

```
public class SpaltenZaehler {

   private static final String NOT_USED = "";

  /**
    * Nimmt einen zweidimensionalen Array, der eine Tabelle darstellt, entgegen. In der ersten
    * Dimension stehen die Zeilen, in der zweiten die Spalten. Dieser Array wird zeilenweise
    * durchgegangen und in jeder Spalte geschaut, ob dord ein leerer String oder null drinnen steht.
    * Dann gilt die Spalte als nicht genutzt. Die Summe der genutzen Spalten wird für jede Zeile
    * in einem int-Array zusammengefasst ausgegeben.
    */
  public int[] genutzteSpaltenProTabelle(Object[][] table) {
    int[] result = new int[table.length];

    for (int zeile = 0; zeile < table.length; zeile++) {
      result[zeile] = genutzteSpaltenProZeile(table[zeile]);
    }
    return result;
  }

  int genutzteSpaltenProZeile(final Object[] zeile) {
     // Im Idealfall sind alle Spalten genutzt, dann ist das Ergebnis die Länge des zeilen-Arrays
     int result = zeile.length;
     for (Object spalte: zeile ) {
        if(!used(spalte) {
          result--;
        }
     }
     return result;
  }

  boolean used(Object obj) {
    return obj != null && !obj.equals(NOT_USED);
  }
}
```

Erstens liest sich so ein Code viel besser als eine dreifach verschachtelte Schleife/If-Verzweigung. Und Du kannst so auch die Methoden einzeln aufrufen und testen, um evtl. vorhandene Fehler im Algorithmus zu finden.


----------



## ARadauer (1. Mrz 2012)

Ich würd auf null überprüfen...

Aber mal ein sehr grundlegender Tipp: Überleg dir wie du es per Hand machen würdest!

Was willst du genau machen? Wenn du eine zeile hast und drei Spalten und in Spalte 1 steht was und 3 auch nur 2 nicht. Wie viele Spalten hast du? 2? Ich denke trotzdem 3 oder?
Was ist wenn in der zweiten Zeile ganz was anderes steht? Überleg dir was du machen willst und dann wie du es selber machen würdest... und dann wie der Computer es machen würde..

also ich würde einfach von rechts rüber gehen und schauen bis einer leer ist... das ist dann die spaltenbreite... natürlich musst du die anderen zeilen auch berücksichtigen und die größte suchen...

zb so...


```
public class Test {

    String[][] data = new String[10][10];

    public void setValue(int row, int col, String value) {
        data[row][col] = value;
    }

    public String getValue(int row, int col) {
        return data[row][col];
    }

    public void printTable() {
        for (int i = 0; i < data.length; i++) {
            for (int y = 0; y < data[i].length; y++) {
                if (data[i][y] == null) {
                    System.out.print(" |");
                }
                else {
                    System.out.print(data[i][y] + "|");
                }
            }
            System.out.println("");
        }
    }

    public int getColumns() {
        int max = 0;
        for (int i = 0; i < data.length; i++) {
            for (int y = data[i].length - 1; y >= 0; y--) {
                if (data[i][y] != null) {
                    if (y + 1 > max) {
                        max = y + 1;
                    }
                    continue;
                }
            }
        }

        return max;

    }

    public static void main(String[] args) {
        Test test = new Test();
        test.setValue(2, 2, "X");
        test.setValue(0, 0, "X");
        test.setValue(8, 4, "O");
        test.printTable();
        System.out.println("Belegte Spalten " + test.getColumns());
    }

}
```


----------



## CEric (5. Mrz 2012)

@ARadauer:
Hm ja du hast recht, ich muss also einfach vorerst für die letzte Zeile Prüfen ob in einer Spalte ein nicht leerer String ist, falls das aber in allen  Spalten der letzten Zeile der Fall ist muss ich das ganze mit der vorletzten Zeile wiederholen!
Kannst du mir vielleicht kurz erklären was du da ganau machst; vor allem den zweiten Teil der for-Schleife!?
MfG


----------



## CEric (6. Mrz 2012)

Also ich hab da noch was, abgeschnitten werden können nur die hinteren Zeilen die leer sind, also wenn Spalte 2 von 3 leer ist kann man diese nicht herausnehmen, da man sonst die Tabelle verfälscht!


----------



## CEric (6. Mrz 2012)

```
public int getColumns() {
		int spalten = 0;

		for (int y = tabelle[0].length; y > 0 ; y--) { 
			
			for (int x = 0; x < tabelle.length; x++) {          

				if (tabelle[x][y] != null) {
					spalten = y;
					return spalten; 

				} else if (tabelle[x][y] == null) { 
					continue;
				}
			}
		}

		return spalten;

	}
```
Also das ist jetzt mal mein Quellcode für die getSpalten.Ich beginne also in der letzten Spalte y und gehe dafür alle Zeilen durch.
Ist tabelle[x][y] != null hab ich ja die längste Zeile gefunden und somit auch die Anzahl Spalten.
Andernfalls muss ich weitermachen, aber ich hab noch das Problem, wenn ich die letzte Spalte "abschneide" muss ich die vorletzte überprüfen usw., stimmt das denn so?


----------

