Program zapisuje dane do tablicy, ale później jest problem z ich wypisaniem

0

W ramach ćwiczeń z programowania obiektowego probuje napisać "aplikacje", która umożliwia wyświetlenie dostępnych piosenek (zapisanych w tablicy), dodania do biblioteki (również tablicy) i wszystko jest dobrze, jeśli podaje wartości w kolejności od 1 do n, gdy chce podać np tylko piosenkę nr 4, to wartość zostaje zapisana do tablicy, ale kiedy chce wyświetlić tablice piosenek z biblioteki, to wtedy nic się nie wyświetla.

import java.util.Scanner;

public class Main {
   public static void main(String[] args) {
       Menu menu = new Menu();
       menu.displayMenu();
   }
}

class Menu {
   void displayMenu() {
       Scanner input = new Scanner(System.in);
       System.out.println("Witaj w aplikacji Muzyka!\n-------------------------");
       System.out.println("1. Pokaż dostępne piosenki");
       System.out.println("2. Pokaż moją bibliotekę");
       System.out.print("Twój wybór: ");

       int choice = input.nextInt();

       switch (choice) {
           case 1:
               Songs.getSongs();
               displaySubMenu();
               displayMenu();
               break;
           case 2:
               Songs.getLibrarySongs();
               break;
           default:
               throw new IllegalStateException(STR."Unexpected value: \{choice}");
       }
   }

   private void displaySubMenu() {
       int choice;
       while (true)
       {
           Scanner input = new Scanner(System.in);
           System.out.println("Czy chcesz dodać piosenke do biblioteki? Podaj jej numer, jeśli nie wprowadź 0");
           choice = input.nextInt();
           if (choice > 0 && choice <= Songs.songs.length) {
               Songs.librarySongs[choice - 1] = Songs.songs[choice - 1];
               if (Songs.librarySongs[choice - 1] != null) {
                   System.out.println(STR."Dodano piosenkę \{Songs.librarySongs[choice - 1]} do biblioteki!");
               } else {
                   System.out.println("Niestety napotkano problem podczas dodawania zmiennej do tablicy!");
               }

           } else if (choice == 0) {
               break;
           } else {
               throw new IllegalStateException(STR."Unexpected value: \{choice}");
           }
       }
   }
}
class Songs {
   static String[] librarySongs = new String[100];
   static String[] songs = {
           "Bohemian Rhapsody - Queen",
           "Hey Jude - The Beatles",
           "Imagine - John Lennon",
           "Hotel California - Eagles",
           "Stairway to Heaven - Led Zeppelin",
           "Let It Be - The Beatles",
           "Yesterday - The Beatles",
           "Like a Rolling Stone - Bob Dylan",
           "I Will Always Love You - Whitney Houston",
           "Smells Like Teen Spirit - Nirvana",
           "Thriller - Michael Jackson",
           "Billie Jean - Michael Jackson",
           "Hallelujah - Leonard Cohen",
           "Sweet Child o' Mine - Guns N' Roses",
           "Wonderwall - Oasis",
           "Boogie Wonderland - Earth, Wind & Fire",
           "Piano Man - Billy Joel",
           "Don't Stop Believin' - Journey",
           "Purple Rain - Prince",
           "Let's Get It On - Marvin Gaye",
           "Eye of the Tiger - Survivor",
           "Livin' on a Prayer - Bon Jovi",
           "I Want to Hold Your Hand - The Beatles",
           "Dancing Queen - ABBA",
           "My Heart Will Go On - Celine Dion",
           "Wonderful Tonight - Eric Clapton",
           "Every Breath You Take - The Police",
           "Girls Just Want to Have Fun - Cyndi Lauper",
           "Stayin' Alive - Bee Gees",
           "Every Rose Has Its Thorn - Poison",
           "Walk This Way - Aerosmith",
           "Another One Bites the Dust - Queen",
           "Take Me Home, Country Roads - John Denver",
           "I Will Survive - Gloria Gaynor",
           "We Are the Champions - Queen",
           "Crazy - Gnarls Barkley",
           "California Dreamin' - The Mamas & The Papas",
           "Let It Go - Idina Menzel",
           "Rolling in the Deep - Adele",
           "Under Pressure - Queen & David Bowie",
           "Dancing in the Dark - Bruce Springsteen",
           "Don't Stop 'Til You Get Enough - Michael Jackson",
           "Oops!... I Did It Again - Britney Spears",
           "Total Eclipse of the Heart - Bonnie Tyler",
           "Bridge Over Troubled Water - Simon & Garfunkel",
           "Wannabe - Spice Girls",
           "Sweet Caroline - Neil Diamond",
           "I Wanna Dance with Somebody - Whitney Houston",
           "Uptown Funk - Mark Ronson ft. Bruno Mars",
           "Achy Breaky Heart - Billy Ray Cyrus",
           "I Want to Know What Love Is - Foreigner",
           "Man in the Mirror - Michael Jackson",
           "Mrs. Robinson - Simon & Garfunkel",
           "Ring of Fire - Johnny Cash",
           "Boys Don't Cry - The Cure",
           "I Believe I Can Fly - R. Kelly",
           "Don't Worry, Be Happy - Bobby McFerrin",
           "Love Shack - The B-52's",
           "With or Without You - U2",
           "Stand by Me - Ben E. King",
           "Hey Ya! - OutKast",
           "Killing Me Softly With His Song - Roberta Flack",
           "All You Need Is Love - The Beatles",
           "My Girl - The Temptations",
           "I Heard It Through the Grapevine - Marvin Gaye",
           "I Love Rock 'n' Roll - Joan Jett & The Blackhearts",
           "American Pie - Don McLean",
           "Suspicious Minds - Elvis Presley",
           "Georgia on My Mind - Ray Charles",
           "I Can't Help Falling in Love - Elvis Presley",
           "Yesterday Once More - Carpenters",
           "Let's Stay Together - Al Green",
           "Brown Eyed Girl - Van Morrison",
           "September - Earth, Wind & Fire",
           "Love Me Tender - Elvis Presley",
           "Baby Got Back - Sir Mix-A-Lot",
           "I Will Always Love You - Dolly Parton",
           "You Are the Sunshine of My Life - Stevie Wonder",
           "Hello - Adele",
           "I Want to Hold Your Hand - The Beatles",
           "Great Balls of Fire - Jerry Lee Lewis",
           "Proud Mary - Creedence Clearwater Revival",
           "We Will Rock You - Queen",
           "Sweet Home Alabama - Lynyrd Skynyrd",
           "Hey There Delilah - Plain White T's",
           "ABC - The Jackson 5",
           "Bennie and the Jets - Elton John",
           "Born to Run - Bruce Springsteen",
           "Brown Sugar - The Rolling Stones",
           "Don't Let the Sun Go Down on Me - Elton John",
           "Free Fallin' - Tom Petty",
           "I Got You (I Feel Good) - James Brown",
           "I'm a Believer - The Monkees",
           "Just the Way You Are - Billy Joel",
           "La Bamba - Ritchie Valens",
           "Like a Prayer - Madonna",
           "Love Story - Taylor Swift",
           "Maggie May - Rod Stewart",
           "Margaritaville - Jimmy Buffett",
           "Oh, Pretty Woman - Roy Orbison"
   };

   static public void getSongs() {
       int i = 0;
       for (String song : songs) {
           i++;
           System.out.println(STR."\{i}.\{song}");
       }
   }
   static public void getLibrarySongs() {
       int i = 0;
       System.out.println("Twoja biblioteka: ");
       for (String song : librarySongs) {
           if (song == null) {
               break;
           }
           i++;
           System.out.println(STR."\{i}.\{song}");
       }
   }
}
2

Co Ty masz z tymi static? Weź wywal to słowo static i tyle. I aktualny podziała na klasy jaki masz też jest raczej okropny. Moim zdaniem wszystko co jest w klasie Song, powinieneś przenieść do Menu, i ewentualnie z tego próbować wydzielić elementy, ale tym razem w odpowiedni sposób.

A co do problemu który masz, problem jest tutaj:

Maciek_SK8 napisał(a):
   static public void getLibrarySongs() {
       int i = 0;
       System.out.println("Twoja biblioteka: ");
       for (String song : librarySongs) {
           if (song == null) {
               break;
           }
           i++;
           System.out.println(STR."\{i}.\{song}");
       }
   }
}

Jak napotkasz null, czyli np pierwszy element to przestajesz printować elementy. Dzieje się tak dlatego, że jak dodasz piosenkę nr 25 do swojej biblioteki, do ona nie będzie na pozycji 1, tylko właśnie 25, bo tak napisałeś swój kod: Songs.librarySongs[choice - 1] = Songs.songs[choice - 1]; że piosenki w bibliotece mają taki sam numer jak piosenki wszystkie.

To co powinieneś zrobić to:

  1. Albo przepisać program z tablic na List<> albo Map<>.
  2. albo zabrać break z pętli, i np napisać:
    if (song != null) {
        System.out.println(STR."\{i}.\{song}");
    }
    i++;
    
0

Jeśli chodzi o to, to użyłem tylko teraz, żeby wygodniej było mi wywołać metody, gdyby wszystko już działało to zrobiłbym zwykle metody, ale jeśli to jest zły nawyk to zaraz wszystko pozmieniam.

Co Ty masz z tymi static? Weź wywal to słowo static i tyle

Właśnie jeszcze nie wiem, jak wszystko dzielić na klasy, żeby było dobrze, ale mam nadzieje, ze poprzez naukę to zrozumiem

I aktualny podziała na klasy jaki masz też jest raczej okropny.

Dzięki bardzo, jakoś nie pomyślałem wcale o tym, ze może to przeszkadzać. Głupi błąd

Jak napotkasz null, czyli np pierwszy element to przestajesz printować elementy. Dzieje się tak dlatego, że jak dodasz piosenkę nr 25 do swojej biblioteki, do ona nie będzie na pozycji 1, tylko właśnie 25, bo tak napisałeś swój kod: Songs.librarySongs[choice - 1] = Songs.songs[choice - 1]; że piosenki w bibliotece mają taki sam numer jak piosenki wszystkie.

Wolałem użyć tablic, bo list, ani map nie mialem jeszcze w kusie

Albo przepisać program z tablic na List<> albo Map<>.

2

Parę tipów:

  1. Nazewnictwo klas i metod:

    • Zamiast Songs możesz użyć czegoś co bardziej opisuje tę klasę czyli np. SongRepository, SongCatalog, SongLibrary
    • Metody które zawierają get w nazwie przeważnie coś zwracają, a przeważnie to co jest napisane po get, czyli nazwy getSongs i getLibrarySongs mówią, że by powinny zwracać piosenki, a one zamiast tego je wypisują na konsolę, tak więc lepszymi nazwami będzie printSongs lub np. displaySongs.
  2. Używanie static w tym kontekście jest złe i zmień klasę Songs na niestatyczną i ogólnie unikaj static dopóki nie zrozumiesz dobrze programowania obiektowego, a żeby się tego nauczyć rób wszystko na obiektach

  3. Enkapsulacja - Jak już zmienisz Songs na niestatyczną postać, to poczytaj o enkapsulacji i o tym że nie powinno się operować bezpośrednio na polach klasy czyli np zmiast:

    Songs.librarySongs[choice - 1] = Songs.songs[choice - 1];
    

    Zrób metody setLibrarySong(index, song) i getSong(index) w klasie Songs które ustawiają i pobierają te dane

    obiektKlasySongs.setLibrarySong(choice - 1,obiektKlasySongs.getSong(choice - 1));
    

    A pola na private:

    private String[] librarySongs = new String[100];
    
  4. Utworzenie obiektu Songs - jak chcesz wiedzieć w którym miejscu go stworzyć i jak go przekazać do miejsc gdzie będziesz wywoływał jego metody (czyli np. do klasy Menu) to poczytaj o dependency injection. Jest to podstawa której wielu początkujących nie ogarnia, a pozwala z łatwością robić kod który jest łatwy w rozbudowie, testowaniu, zmianie i warto się tego nauczyć jako jedną z pierwszych rzeczy, bo później ciężko zmienić niektóre przyzwyczajenia.

  5. Jak chcesz rozbudować ten kod to od razu zastanów się czy twoja klasa Songs przypadkiem nie robi dwóch lub więcej różnych rzeczy (poczytaj o singleResposibility) i czy nie lepiej ją od razu podzielić na np. SongCatalog (zawiera wszystkie piosenki) i SongLibrary (zajmuje się piosenkami w bibliotece usera albo nawet bardziej np. SongDisplay który wyświetla piosenki itd..
    Po co takie rozdzielanie? Jak np. by ci się rozrósł ten program i byś chciał przechowywać piosenki w bazie danych, to przy podziale na np. SongCatalog, SongLibrary, SongDisplay możesz po prostu zamienić implementację SongCatalog na np. SongDatabase czy jakieś SongRepository i nic nie zmieniać w SongLibrary i SongDisplay. A przy braku podziału będziesz musiał cały kod zajmujący się library i wyświetlaniem przekopiować też do nowej klasy z bazą danych, albo dopiero wtedy przenieść do oddzielnych klas, co przy rozbudowanej aplikacji może się okazać ciężkim zadaniem.

0

Dzięki za te wskazówki, będę teraz na to zwracał uwagę

Luciferrrro napisał(a):

Parę tipów:

  • Zamiast Songs możesz użyć czegoś co bardziej opisuje tę klasę czyli np. SongRepository, SongCatalog, SongLibrary
  • Metody które zawierają get w nazwie przeważnie coś zwracają, a przeważnie to co jest napisane po get, czyli nazwy getSongs i getLibrarySongs mówią, że by powinny zwracać piosenki, a one zamiast tego je wypisują na konsolę, tak więc lepszymi nazwami będzie printSongs lub np. displaySongs.

Dobra, to nie będę już wcale tego używał

  1. Używanie static w tym kontekście jest złe i zmień klasę Songs na niestatyczną i ogólnie unikaj static dopóki nie zrozumiesz dobrze programowania obiektowego, a żeby się tego nauczyć rób wszystko na obiektach

ogólnie wiem mniej więcej o co chodzi i nie wiem czemu nie pomyślałem o zastosowaniu tego w tym przypadku

  1. Enkapsulacja - Jak już zmienisz Songs na niestatyczną postać, to poczytaj o enkapsulacji i o tym że nie powinno się operować bezpośrednio na polach klasy czyli np zmiast:

Zaraz sobie wszystko poczytam i dzięki za podpowiedź

  1. Utworzenie obiektu Songs - jak chcesz wiedzieć w którym miejscu go stworzyć i jak go przekazać do miejsc gdzie będziesz wywoływał jego metody (czyli np. do klasy Menu) to poczytaj o dependency injection. Jest to podstawa której wielu początkujących nie ogarnia, a pozwala z łatwością robić kod który jest łatwy w rozbudowie, testowaniu, zmianie i warto się tego nauczyć jako jedną z pierwszych rzeczy, bo później ciężko zmienić niektóre przyzwyczajenia.

O rozbudowaniu w sumie nie myślałem, ale jest to dobry pomysł, kiedy będę już na bardziej zaawansowanym poziomie

  1. Jak chcesz rozbudować ten kod to od razu zastanów się czy twoja klasa Songs przypadkiem nie robi dwóch lub więcej różnych rzeczy (poczytaj o singleResposibility) i czy nie lepiej ją od razu podzielić na np. SongCatalog (zawiera wszystkie piosenki) i SongLibrary (zajmuje się piosenkami w bibliotece usera albo nawet bardziej np. SongDisplay który wyświetla piosenki itd..
    Po co takie rozdzielanie? Jak np. by ci się rozrósł ten program i byś chciał przechowywać piosenki w bazie danych, to przy podziale na np. SongCatalog, SongLibrary, SongDisplay możesz po prostu zamienić implementację SongCatalog na np. SongDatabase czy jakieś SongRepository i nic nie zmieniać w SongLibrary i SongDisplay. A przy braku podziału będziesz musiał cały kod zajmujący się library i wyświetlaniem przekopiować też do nowej klasy z bazą danych, albo dopiero wtedy przenieść do oddzielnych klas, co przy rozbudowanej aplikacji może się okazać ciężkim zadaniem.

Jeszcze raz dzięki za wszystkie rady, na kursie, z którego się uczę jest tylko proste przykładowe zastosowanie, ale teraz zrozumiałem, żeby opanować dobrze materiał trzeba cały czas pisać kod, a nie oglądać tylko kurs i napisać podobny kod, jak w odcinku

2
Luciferrrro napisał(a):

Parę tipów:

  1. Nazewnictwo klas i metod:
    • Zamiast Songs możesz użyć czegoś co bardziej opisuje tę klasę czyli np. SongRepository, SongCatalog, SongLibrary

Tak jak zgadzam się że nazewnictwo klas jest bardzo ważne, tak nie widzę czemu dopisanie Repository, Catalog albo Library dało cokolwiek. Co więcej dają te zarostki, to są jakieś "filler wordy", lanie wody.

Luciferrrro napisał(a):
  • Metody które zawierają get w nazwie przeważnie coś zwracają, a przeważnie to co jest napisane po get, czyli nazwy getSongs i getLibrarySongs mówią, że by powinny zwracać piosenki, a one zamiast tego je wypisują na konsolę, tak więc lepszymi nazwami będzie printSongs lub np. displaySongs.

Tutaj się zgadzam na 100%.

Luciferrrro napisał(a):
  1. Używanie static w tym kontekście jest złe i zmień klasę Songs na niestatyczną i ogólnie unikaj static dopóki nie zrozumiesz dobrze programowania obiektowego, a żeby się tego nauczyć rób wszystko na obiektach

Z unikaniem staticów się zgadzam, ale używanie obiektów to jeszcze nie programowanie obiektowe.

Luciferrrro napisał(a):
  1. Enkapsulacja - Jak już zmienisz Songs na niestatyczną postać, to poczytaj o enkapsulacji i o tym że nie powinno się operować bezpośrednio na polach klasy czyli np zmiast:

    Songs.librarySongs[choice - 1] = Songs.songs[choice - 1];
    

    Zrób metody setLibrarySong(index, song) i getSong(index) w klasie Songs które ustawiają i pobierają te dane

    obiektKlasySongs.setLibrarySong(choice - 1,obiektKlasySongs.getSong(choice - 1));
    

    A pola na private:

    private String[] librarySongs = new String[100];
    

Tak jak się zgadzam z enkapsulacją, tak Twój przykład nic nie daje, zamiana pola na setter/getter to jest nadal ten sam poziom abstrakcji, tylko zaciemniłeś całość. To nie jest enkapsulacja niestety. Należałoby to lepiej zrobić.

Luciferrrro napisał(a):
  1. Utworzenie obiektu Songs - jak chcesz wiedzieć w którym miejscu go stworzyć i jak go przekazać do miejsc gdzie będziesz wywoływał jego metody (czyli np. do klasy Menu) to poczytaj o dependency injection. Jest to podstawa której wielu początkujących nie ogarnia, a pozwala z łatwością robić kod który jest łatwy w rozbudowie, testowaniu, zmianie i warto się tego nauczyć jako jedną z pierwszych rzeczy, bo później ciężko zmienić niektóre przyzwyczajenia.

Ja bym w to nie szedł na początku, zwłaszcza że nie ma testów i use-case'u. Tylko mu zaciemni.

Luciferrrro napisał(a):
  1. Jak chcesz rozbudować ten kod to od razu zastanów się czy twoja klasa Songs przypadkiem nie robi dwóch lub więcej różnych rzeczy (poczytaj o singleResposibility) i czy nie lepiej ją od razu podzielić na np. SongCatalog (zawiera wszystkie piosenki) i SongLibrary (zajmuje się piosenkami w bibliotece usera albo nawet bardziej np. SongDisplay który wyświetla piosenki itd..

Ta klasa teraz nie ma żadnej logiki, więc raczej nie robi dwóch rzeczy. Bliżej jej do anemicznej struktury niż klasy.

Luciferrrro napisał(a):

Po co takie rozdzielanie? Jak np. by ci się rozrósł ten program i byś chciał przechowywać piosenki w bazie danych, to przy podziale na np. SongCatalog, SongLibrary, SongDisplay możesz po prostu zamienić implementację SongCatalog na np. SongDatabase czy jakieś SongRepository i nic nie zmieniać w SongLibrary i SongDisplay. A przy braku podziału będziesz musiał cały kod zajmujący się library i wyświetlaniem przekopiować też do nowej klasy z bazą danych, albo dopiero wtedy przenieść do oddzielnych klas, co przy rozbudowanej aplikacji może się okazać ciężkim zadaniem.

YAGNI. Robienie czegoś "na wszelki wypadek" jest słabe.

To o czym mówisz z podmianą implementacji to jest dobra rzecz; ale gość widać żę dopiero zaczyna więc takie rady mu na ten moment nie pomogą, tylko zaciemnią całość.

Maciek_SK8 napisał(a):

Jeszcze raz dzięki za wszystkie rady, na kursie, z którego się uczę jest tylko proste przykładowe zastosowanie, ale teraz zrozumiałem, żeby opanować dobrze materiał trzeba cały czas pisać kod, a nie oglądać tylko kurs i napisać podobny kod, jak w odcinku

@Maciek_SK8: Podeślij linik do tego kursu który masz.

0
Riddle napisał(a):

To jak mógłbym to zrobić lepiej na etapie nauki, na którym jestem?

Tak jak się zgadzam z enkapsulacją, tak Twój przykład nic nie daje, zamiana pola na setter/getter to jest nadal ten sam poziom abstrakcji, tylko zaciemniłeś całość. To nie jest enkapsulacja niestety. Należałoby to lepiej zrobić.

@Riddle to jest ten kurs (wiem, ze ma swoje lata, ale powiedzmy, ze go dostałem), jak cos to skończyłem dział programowanie obiektowe, jeśli chodzi o odcinki kursu: https://www.udemy.com/course/java-od-podstaw-do-eksperta-tworz-wasne-aplikacje/?couponCode=GENAISALE24

@Maciek_SK8: Podeślij linik do tego kursu który masz.

0

@Riddle @Luciferrrro na podstawie Waszych wskazówek poprawiłem ten kod i doszedłem do takiego momentu:

import java.util.Arrays;
import java.util.Comparator;
import java.util.Scanner;

public class Main {
    public static void main(String[] args) {
        Menu menu = new Menu();
        menu.displayMenu();
    }
}

class Menu {
    Scanner input = new Scanner(System.in);
    SongCatalog catalog = new SongCatalog();
    UserLibrary library = new UserLibrary();
    SongDisplay songDisplay = new SongDisplay();

    void displayMenu() {
        System.out.println("\nWitaj w aplikacji Muzyka!\n-------------------------");
        System.out.println("1. Pokaż dostępne piosenki");
        System.out.println("2. Pokaż moją bibliotekę");
        System.out.println("3. Zakończyć dzialanie programu");
        System.out.print("Twój wybór: ");

        int choice = input.nextInt();

        switch (choice) {
            case 1:
                System.out.println();
                songDisplay.displaySong(catalog.getSongs());
                displaySongsSubMenu();
                displayMenu();
                break;
            case 2:
                System.out.println("\nTwoja biblioteka: ");
                songDisplay.displaySong(library.getSongs());
                displayLibrarySubMenu();
                break;
            case 3:
                System.out.println("Dziękuję za skorzystanie z programu");
                break;
            default:
                throw new IllegalStateException(STR."Unexpected value: \{choice}");
        }
    }

    private void displaySongsSubMenu() {
        int choice;
        int i = 0;
        while (true)
        {
            System.out.println("Czy chcesz dodać piosenke do biblioteki? Podaj jej numer, jeśli nie wprowadź 0");
            choice = input.nextInt();
            if (choice > 0 && choice <= 100) {
                library.setUserLibrarySong((i), (catalog.getSong(choice - 1)));
                if (library.getSong(i) != null) {
                    System.out.println(STR."Dodano piosenkę \{library.getSong(i)} do biblioteki!");
                    i++;
                } else {
                    System.out.println("Niestety napotkano problem podczas dodawania zmiennej do tablicy!");
                }
            } else if (choice == 0) {
                break;
            } else {
                throw new IllegalStateException(STR."Unexpected value: \{choice}");
            }
        }
    }
    private void displayLibrarySubMenu() {
        int choice;
        System.out.println("\nCo chcesz teraz zrobić?");
        System.out.println("1. Posortowac bibliotekę rosnąco");
        System.out.println("2. Posortowac bibliotekę malejąco");
        System.out.println("3. Wyjść do menu głównego");
        System.out.print("Twój wybór: ");
        choice = input.nextInt();

        switch (choice) {
            case 1:
                Arrays.sort(library.getSongs(), Comparator.nullsLast(Comparator.naturalOrder()));
                System.out.println("\nPosortowano tablicę malejąco");
                songDisplay.displaySong(library.getSongs());
                displayMenu();
                break;
            case 2:
                Arrays.sort(library.getSongs(), Comparator.nullsLast(Comparator.reverseOrder()));
                System.out.println("\nPosortowano tablicę malejąco");
                songDisplay.displaySong(library.getSongs());
                displayMenu();
                break;
            case 3:
                displayMenu();
                break;
            default:
                throw new IllegalStateException(STR."Unexpected value: \{choice}");
        }
    }
}

class SongCatalog {
    private final String[] songCatalog = {
        "Bohemian Rhapsody - Queen",
                "Hey Jude - The Beatles",
                "Imagine - John Lennon",
                "Hotel California - Eagles",
                "Stairway to Heaven - Led Zeppelin",
                "Let It Be - The Beatles",
                "Yesterday - The Beatles",
                "Like a Rolling Stone - Bob Dylan",
                "I Will Always Love You - Whitney Houston",
                "Smells Like Teen Spirit - Nirvana",
                "Thriller - Michael Jackson",
                "Billie Jean - Michael Jackson",
                "Hallelujah - Leonard Cohen",
                "Sweet Child o' Mine - Guns N' Roses",
                "Wonderwall - Oasis",
                "Boogie Wonderland - Earth, Wind & Fire",
                "Piano Man - Billy Joel",
                "Don't Stop Believin' - Journey",
                "Purple Rain - Prince",
                "Let's Get It On - Marvin Gaye",
                "Eye of the Tiger - Survivor",
                "Livin' on a Prayer - Bon Jovi",
                "I Want to Hold Your Hand - The Beatles",
                "Dancing Queen - ABBA",
                "My Heart Will Go On - Celine Dion",
                "Wonderful Tonight - Eric Clapton",
                "Every Breath You Take - The Police",
                "Girls Just Want to Have Fun - Cyndi Lauper",
                "Stayin' Alive - Bee Gees",
                "Every Rose Has Its Thorn - Poison",
                "Walk This Way - Aerosmith",
                "Another One Bites the Dust - Queen",
                "Take Me Home, Country Roads - John Denver",
                "I Will Survive - Gloria Gaynor",
                "We Are the Champions - Queen",
                "Crazy - Gnarls Barkley",
                "California Dreamin' - The Mamas & The Papas",
                "Let It Go - Idina Menzel",
                "Rolling in the Deep - Adele",
                "Under Pressure - Queen & David Bowie",
                "Dancing in the Dark - Bruce Springsteen",
                "Don't Stop 'Til You Get Enough - Michael Jackson",
                "Oops!... I Did It Again - Britney Spears",
                "Total Eclipse of the Heart - Bonnie Tyler",
                "Bridge Over Troubled Water - Simon & Garfunkel",
                "Wannabe - Spice Girls",
                "Sweet Caroline - Neil Diamond",
                "I Wanna Dance with Somebody - Whitney Houston",
                "Uptown Funk - Mark Ronson ft. Bruno Mars",
                "Achy Breaky Heart - Billy Ray Cyrus",
                "I Want to Know What Love Is - Foreigner",
                "Man in the Mirror - Michael Jackson",
                "Mrs. Robinson - Simon & Garfunkel",
                "Ring of Fire - Johnny Cash",
                "Boys Don't Cry - The Cure",
                "I Believe I Can Fly - R. Kelly",
                "Don't Worry, Be Happy - Bobby McFerrin",
                "Love Shack - The B-52's",
                "With or Without You - U2",
                "Stand by Me - Ben E. King",
                "Hey Ya! - OutKast",
                "Killing Me Softly With His Song - Roberta Flack",
                "All You Need Is Love - The Beatles",
                "My Girl - The Temptations",
                "I Heard It Through the Grapevine - Marvin Gaye",
                "I Love Rock 'n' Roll - Joan Jett & The Blackhearts",
                "American Pie - Don McLean",
                "Suspicious Minds - Elvis Presley",
                "Georgia on My Mind - Ray Charles",
                "I Can't Help Falling in Love - Elvis Presley",
                "Yesterday Once More - Carpenters",
                "Let's Stay Together - Al Green",
                "Brown Eyed Girl - Van Morrison",
                "September - Earth, Wind & Fire",
                "Love Me Tender - Elvis Presley",
                "Baby Got Back - Sir Mix-A-Lot",
                "I Will Always Love You - Dolly Parton",
                "You Are the Sunshine of My Life - Stevie Wonder",
                "Hello - Adele",
                "I Want to Hold Your Hand - The Beatles",
                "Great Balls of Fire - Jerry Lee Lewis",
                "Proud Mary - Creedence Clearwater Revival",
                "We Will Rock You - Queen",
                "Sweet Home Alabama - Lynyrd Skynyrd",
                "Hey There Delilah - Plain White T's",
                "ABC - The Jackson 5",
                "Bennie and the Jets - Elton John",
                "Born to Run - Bruce Springsteen",
                "Brown Sugar - The Rolling Stones",
                "Don't Let the Sun Go Down on Me - Elton John",
                "Free Fallin' - Tom Petty",
                "I Got You (I Feel Good) - James Brown",
                "I'm a Believer - The Monkees",
                "Just the Way You Are - Billy Joel",
                "La Bamba - Ritchie Valens",
                "Like a Prayer - Madonna",
                "Love Story - Taylor Swift",
                "Maggie May - Rod Stewart",
                "Margaritaville - Jimmy Buffett",
                "Oh, Pretty Woman - Roy Orbison" };

    public String[] getSongs() {
        return songCatalog;
    }

    public String getSong(int index) {
        return songCatalog[index];
    }
}

class UserLibrary {
    private final String[] userLibrary = new String[100];

    public String getSong(int index) {
        return userLibrary[index];
    }

    public String[] getSongs() {
        return userLibrary;
    }

    public void setUserLibrarySong(int index, String song) {
        this.userLibrary[index] = song;
    }
}

class SongDisplay {
    void displaySong(String[] songs) {
        int i = 0;
        for (String song : songs) {
            if (song != null) {
                i++;
                System.out.println(STR."\{i}. \{song}");
            }
        }
    }
}

Jest tu coś, co ewentualnie mógłbym poprawić, żeby kod był czytelniejszy i lepiej napisany?

0
Maciek_SK8 napisał(a):

@Riddle @Luciferrrro na podstawie Waszych wskazówek poprawiłem ten kod i doszedłem do takiego momentu:

Sorry, ale niestety ten nowy kod który napisałeś jest gorszy niż poprzedni 😕 Te nowe klasy które dodałeś nic dobrego nie wnoszą, tylko zaciemniają kod. Moim zdaniem powinieneś wrócić do pierwszego który miałeś, i tak jak mówiłem złączyć klasy Songs i Menu w jedną.

Maciek_SK8 napisał(a):
Riddle napisał(a):

To jak mógłbym to zrobić lepiej na etapie nauki, na którym jestem?

Tak jak się zgadzam z enkapsulacją, tak Twój przykład nic nie daje, zamiana pola na setter/getter to jest nadal ten sam poziom abstrakcji, tylko zaciemniłeś całość. To nie jest enkapsulacja niestety. Należałoby to lepiej zrobić.

Moim zdaniem nie powinieneś się tym przejmować na razie. Enkapsulacja to jest dosyć delikatny temat, ciężko to zrobić dobrze.

Maciek_SK8 napisał(a):

@Riddle to jest ten kurs (wiem, ze ma swoje lata, ale powiedzmy, ze go dostałem), jak cos to skończyłem dział programowanie obiektowe, jeśli chodzi o odcinki kursu: https://www.udemy.com/course/java-od-podstaw-do-eksperta-tworz-wasne-aplikacje/?couponCode=GENAISALE24

@Maciek_SK8: Podeślij linik do tego kursu który masz.

No taki średniej jakości ten kurs powiedziałbym, ale zawsze coś. Trochę mnie martwi że nie ma ani słowa o testach automatycznych tutaj.

0

Zaraz dodam wszystko do jednej klasy, ale mam jeszcze pytanie jak się nauczyć podziału na klasy, mam na myśli, kiedy robić wszystko w jednej, kiedy rozdzielać na więcej klas, czy na moim poziomie wszystko raczej dawać do jednej? W jaki sposób mogę to wszystko ćwiczyć, żeby, jak najlepiej zrozumieć zastosowanie tego w praktyce, a nie tylko na przykładzie klasy osoba?

Riddle napisał(a):

Sorry, ale niestety ten nowy kod który napisałeś jest gorszy niż poprzedni 😕 Te nowe klasy które dodałeś nic dobrego nie wnoszą, tylko zaciemniają kod. Moim zdaniem powinieneś wrócić do pierwszego który miałeś, i tak jak mówiłem złączyć klasy Songs i Menu w jedną.

Jak już przerobie cały ten kurs, to wiadomo szukałbym następnego, w którym są zawarte bardziej zaawansowane zagadnienia

No taki średniej jakości ten kurs powiedziałbym, ale zawsze coś. Trochę mnie martwi że nie ma ani słowa o testach automatycznych tutaj.

1
Maciek_SK8 napisał(a):

Zaraz dodam wszystko do jednej klasy, ale mam jeszcze pytanie jak się nauczyć podziału na klasy, mam na myśli, kiedy robić wszystko w jednej, kiedy rozdzielać na więcej klas, czy na moim poziomie wszystko raczej dawać do jednej? W jaki sposób mogę to wszystko ćwiczyć, żeby, jak najlepiej zrozumieć zastosowanie tego w praktyce, a nie tylko na przykładzie klasy osoba?

Jak pytasz jak się nauczyć podziału na klasy, to to jest właściwie pytanie "jak dobrze projektować software", a to nie jest prosta rzecz.

  1. Nie staraj się dzielić programu na klasy, tylko po to żeby były
  2. Na początku, nie kieruj się tym że plik jest duży, to trzeba go podzielić - to droga do nikąd.

Rule of thumb dla Ciebie - to jak pracujesz z jakimiś danymi, które zazwyczaj się poruszają razem - np. numer piosenki i jej tytuł - to te dwie elementy można wsadzić w obiekt. Tylko jak coś takiego zrobisz, to powinieneś od razu to komuś pokazać kto się zna, żeby Ci powiedział czy taka zagrywka ma sens, czy nie. Bo najpewniej na początku nie będzie miała.

Ale się nie przejmuj na razie tym w sumie. Nie staraj się dzielić programu na klasy tylko po to żeby były.

0

Czyli chodzi o to, żeby stworzyć w tym przypadku klasę Song, która będzie miała właściwości np id, name, Author zamiast tworzenia tablicy?

Riddle napisał(a):

Rule of thumb dla Ciebie - to jak pracujesz z jakimiś danymi, które zazwyczaj się poruszają razem - np. numer piosenki i jej tytuł - to te dwie elementy można wsadzić w obiekt. Tylko jak coś takiego zrobisz, to powinieneś od razu to komuś pokazać kto się zna, żeby Ci powiedział czy taka zagrywka ma sens, czy nie. Bo najpewniej na początku nie będzie miała.

To, czego powinien się teraz uczyć i jak? Iść dalej z kursem i gdy będą bardziej zaawansowane rzeczy, to wtedy łatwiej będzie zrozumieć programowanie obiektowe na przykładach używanych przy tworzeniu aplikacji itd? Czy tworzyć takie "aplikacje" podobne do tej, żeby wszystko poćwiczyć?

Riddle napisał(a):

Ale się nie przejmuj na razie tym w sumie. Nie staraj się dzielić programu na klasy tylko po to żeby były.

1
Maciek_SK8 napisał(a):

Czyli chodzi o to, żeby stworzyć w tym przypadku klasę Song, która będzie miała właściwości np id, name, Author zamiast tworzenia tablicy?

Riddle napisał(a):

Rule of thumb dla Ciebie - to jak pracujesz z jakimiś danymi, które zazwyczaj się poruszają razem - np. numer piosenki i jej tytuł - to te dwie elementy można wsadzić w obiekt. Tylko jak coś takiego zrobisz, to powinieneś od razu to komuś pokazać kto się zna, żeby Ci powiedział czy taka zagrywka ma sens, czy nie. Bo najpewniej na początku nie będzie miała.

Jak już mówiłem - na razie połącz Songs z Menu, i trzymaj wszystko w jednej.

Maciek_SK8 napisał(a):

To, czego powinien się teraz uczyć i jak? Iść dalej z kursem i gdy będą bardziej zaawansowane rzeczy, to wtedy łatwiej będzie zrozumieć programowanie obiektowe na przykładach używanych przy tworzeniu aplikacji itd? Czy tworzyć takie "aplikacje" podobne do tej, żeby wszystko poćwiczyć?

Riddle napisał(a):

Ale się nie przejmuj na razie tym w sumie. Nie staraj się dzielić programu na klasy tylko po to żeby były.

Po pierwsze, używanie klas i obiektów to jeszcze nie programowanie obiektowe. Nazwa jest myląca. Tak samo jak po prostu używanie funkcji to jeszcze nie programowanie funkcyjne.

Po drugie, myślę że tak, myślę że pisz programy i nie staraj się dzielić kodu na klasy na siłę.

1 użytkowników online, w tym zalogowanych: 0, gości: 1