diff --git a/build.gradle.kts b/build.gradle.kts index 72be7ed..423272d 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -1,10 +1,15 @@ plugins { id("java") + id("application") } group = "ru.urfu" version = "1.0-SNAPSHOT" +application { + mainClass = "ru.urfu.Main" +} + repositories { mavenCentral() } @@ -12,8 +17,10 @@ repositories { dependencies { testImplementation(platform("org.junit:junit-bom:5.10.0")) testImplementation("org.junit.jupiter:junit-jupiter") + testImplementation("org.jfree:jfreechart:1.5.6") + implementation("org.jfree:jfreechart:1.5.6") } tasks.test { useJUnitPlatform() -} \ No newline at end of file +} diff --git a/src/main/java/ru/urfu/Main.java b/src/main/java/ru/urfu/Main.java index 5845f6d..bf96a0e 100644 --- a/src/main/java/ru/urfu/Main.java +++ b/src/main/java/ru/urfu/Main.java @@ -1,17 +1,25 @@ package ru.urfu; -//TIP To Run code, press or -// click the icon in the gutter. +import java.util.List; + +import ru.urfu.resolver.Task1; +import ru.urfu.model.Player; +import ru.urfu.model.Position; +import ru.urfu.resolver.Task1; +import ru.urfu.io.CSVReader; +import ru.urfu.io.GraphDrawer; + public class Main { public static void main(String[] args) { - //TIP Press with your caret at the highlighted text - // to see how GIGA IDE suggests fixing it. - System.out.printf("Hello and welcome!"); + List players = CSVReader.readFromFile(args[1]); + Task1 task1 = new Task1(players); + + System.out.printf("Task1:\n"); + System.out.printf("Игроков без агенства: %s\n", task1.getCountWithoutAgency()); + System.out.printf("Наибольшее число голов у игрока из числа защитников: %s\n", task1.getMaxDefenderGoalsCount()); + System.out.printf("Позиция самого дорогого немецкого игрока: %s\n", task1.getTheExpensiveGermanPlayerPosition()); + System.out.printf("Команда с наибольшим средним числом удалений на одного игрока: %s\n", task1.getTheRudestTeam()); - for (int i = 1; i <= 5; i++) { - //TIP Press to start debugging your code. We have set one breakpoint - // for you, but you can always add more by pressing . - System.out.println("i = " + i); - } + GraphDrawer.displayGraph3D(players); } -} \ No newline at end of file +} diff --git a/src/main/java/ru/urfu/io/CSVReader.java b/src/main/java/ru/urfu/io/CSVReader.java new file mode 100644 index 0000000..6c8c499 --- /dev/null +++ b/src/main/java/ru/urfu/io/CSVReader.java @@ -0,0 +1,45 @@ +package ru.urfu.io; + +import java.io.IOException; +import java.nio.file.Paths; +import java.util.Scanner; +import java.util.ArrayList; + +import ru.urfu.model.Player; +import ru.urfu.model.Position; + +public class CSVReader { + public static ArrayList readFromFile(String path) { + var playersList = new ArrayList(); + Scanner scan; + try { + scan = new Scanner(Paths.get(path)); + } catch (IOException e) { + return playersList; + } + + scan.nextLine(); + while (scan.hasNextLine()) { + playersList.add(convertRow2Player(scan.nextLine())); + } + return playersList; + } + + private static Player convertRow2Player(String row) { + var elems = row.split(";"); + return new Player( + elems[0], + elems[1], + elems[2], + Position.valueOf(elems[3]), + elems[4], + elems[5], + Integer.parseInt(elems[6]), + Integer.parseInt(elems[7]), + Integer.parseInt(elems[8]), + Integer.parseInt(elems[9]), + Integer.parseInt(elems[10]), + Integer.parseInt(elems[11]) + ); + } +} diff --git a/src/main/java/ru/urfu/io/Graph3D.java b/src/main/java/ru/urfu/io/Graph3D.java new file mode 100644 index 0000000..4467870 --- /dev/null +++ b/src/main/java/ru/urfu/io/Graph3D.java @@ -0,0 +1,29 @@ +import java.io.*; + +import org.jfree.chart.ChartFactory; +import org.jfree.chart.JFreeChart; +import org.jfree.chart.plot.PiePlot3D; +import org.jfree.data.general.DefaultPieDataset; + +public class Graph3D { + + public static void main( String[ ] args ) throws Exception { + DefaultPieDataset dataset = new DefaultPieDataset( ); + dataset.setValue( "IPhone 5s" ,20); + dataset.setValue( "SamSung Grand" , 20); + dataset.setValue( "MotoG" , 40); + dataset.setValue( "Nokia Lumia" , 10); + + JFreeChart chart = ChartFactory.createPieChart3D( + "Mobile Sales" , // chart title + dataset , // data + true , // include legend + true, + false); + + final PiePlot3D plot = ( PiePlot3D ) chart.getPlot( ); + plot.setStartAngle( 270 ); + plot.setForegroundAlpha( 0.60f ); + plot.setInteriorGap( 0.02 ); + } +} diff --git a/src/main/java/ru/urfu/io/GraphDrawer.java b/src/main/java/ru/urfu/io/GraphDrawer.java new file mode 100644 index 0000000..eadcb27 --- /dev/null +++ b/src/main/java/ru/urfu/io/GraphDrawer.java @@ -0,0 +1,98 @@ +package ru.urfu.io; + +import ru.urfu.model.Position; +import ru.urfu.model.Player; + +import java.text.DecimalFormat; +import java.util.Map; +import java.util.HashMap; +import java.util.List; + +import org.jfree.chart.ChartFactory; +import org.jfree.chart.ChartFrame; +import org.jfree.chart.JFreeChart; +import org.jfree.chart.labels.StandardPieSectionLabelGenerator; +import org.jfree.chart.plot.PiePlot; +import org.jfree.chart.plot.PiePlot3D; +import org.jfree.chart.plot.Plot; +import org.jfree.data.general.DefaultPieDataset; + +import java.awt.Color; + +public class GraphDrawer { + static public Map prepareData(List players) { + Map out = new HashMap(); + Integer count; + for (Player p: players) { + count = out.get(p.position()); + if(count == null) { + count = 0; + } + count ++; + out.put(p.position(), count); + } + for (Position pos: Position.values()) { + if(out.get(pos) == null) { + out.put(pos, 0); + } + } + return out; + } + + static public void displayGraph(List players) { + Map data = prepareData(players); + DefaultPieDataset dataset = new DefaultPieDataset<>(); + + data.forEach((pos, count) -> dataset.setValue(pos.getTitle(), count)); + + JFreeChart chart = ChartFactory.createPieChart( + "Распределение по позициям", dataset, true, true, false + ); + + PiePlot plot = (PiePlot) chart.getPlot(); + plot.setLabelGenerator( + new StandardPieSectionLabelGenerator( + "{0}: {1} ({2})", + new DecimalFormat("0"), + new DecimalFormat("0.00%") + ) + ); + plot.setSimpleLabels(true); + plot.setLabelBackgroundPaint(Color.WHITE); + + ChartFrame frame = new ChartFrame("Распределение по позициям", chart); + frame.pack(); + frame.setAlwaysOnTop(true); + frame.setVisible(true); + } + + static public void displayGraph3D(List players) { + Map data = prepareData(players); + DefaultPieDataset dataset = new DefaultPieDataset<>(); + + data.forEach((pos, count) -> dataset.setValue(pos.getTitle(), count)); + + JFreeChart chart = ChartFactory.createPieChart3D( + "Распределение по позициям", dataset, true, true, false + ); + + PiePlot3D plot = (PiePlot3D) chart.getPlot(); + plot.setLabelGenerator( + new StandardPieSectionLabelGenerator( + "{0}: {1} ({2})", + new DecimalFormat("0"), + new DecimalFormat("0.00%") + ) + ); + plot.setSimpleLabels(true); + plot.setLabelBackgroundPaint(Color.WHITE); + plot.setStartAngle( 270 ); + plot.setForegroundAlpha( 0.60f ); + plot.setInteriorGap( 0.02 ); + + ChartFrame frame = new ChartFrame("Распределение по позициям", chart); + frame.pack(); + frame.setAlwaysOnTop(true); + frame.setVisible(true); + } +} diff --git a/src/main/java/ru/urfu/model/Player.java b/src/main/java/ru/urfu/model/Player.java new file mode 100644 index 0000000..0e6f569 --- /dev/null +++ b/src/main/java/ru/urfu/model/Player.java @@ -0,0 +1,18 @@ +package ru.urfu.model; + +public record Player( + String name, + String team, + String city, + Position position, + String nationality, + String agency, + int transfer_cost, + int matches, + int goals, + int assists, + int yellow_cards, + int red_cards +) { + +} diff --git a/src/main/java/ru/urfu/model/Position.java b/src/main/java/ru/urfu/model/Position.java new file mode 100644 index 0000000..4f0d92f --- /dev/null +++ b/src/main/java/ru/urfu/model/Position.java @@ -0,0 +1,20 @@ +package ru.urfu.model; + +public enum Position { + MIDFIELD("полузащитник", "ru"), + DEFENDER("защитник", "ru"), + FORWARD("нападающий", "ru"), + GOALKEEPER("вратарь", "ru"); + + private final String title; + private final String lang; + + Position(String title, String lang) { + this.title = title; + this.lang = lang; + } + + public String getTitle() { + return this.title; + } +}; diff --git a/src/main/java/ru/urfu/resolver/Task1.java b/src/main/java/ru/urfu/resolver/Task1.java new file mode 100644 index 0000000..eba82c7 --- /dev/null +++ b/src/main/java/ru/urfu/resolver/Task1.java @@ -0,0 +1,84 @@ +package ru.urfu.resolver; + +import java.util.Comparator; +import java.util.List; +import java.util.Map; +import java.util.HashMap; + +import ru.urfu.model.Position; +import ru.urfu.model.Player; + +public class Task1 implements IResolver { + + private final List players; + + public Task1(List players) { + this.players = players; + } + + public int getCountWithoutAgency() { + return (int) players + .stream() + .filter(p -> p.agency().isEmpty()) + .count(); + } + + public int getMaxDefenderGoalsCount() { + return players.stream() + .filter(p -> p.position().equals(Position.DEFENDER)) + .mapToInt(Player::goals) + .max() + .orElse(0); + } + + public String getTheExpensiveGermanPlayerPosition() { + return players.stream() + .filter( + p -> p.nationality().equals("Germany") + ) + .max(Comparator.comparing(Player::transfer_cost)) + .map(Player::position) + .map(Position::getTitle) + .orElse(null); + } + + public String getTheRudestTeam() { + Map team2playersNum = new HashMap<>(); + Map team2playersRedCards = new HashMap<>(); + Integer count; + + for (Player p: players) { + if(p.team().isEmpty()) { + continue; + } + + count = team2playersNum.get(p.team()); + if(count == null) { + count = 0; + } + count ++; + team2playersNum.put(p.team(), count); + + count = team2playersRedCards.get(p.team()); + if(count == null) { + count = 0; + } + count += p.red_cards(); + team2playersRedCards.put(p.team(), count); + } + double best = 0.0; + double cur; + String best_team = null; + for (Map.Entry team: team2playersNum.entrySet()) { + cur = ( + team2playersRedCards.get(team.getKey()) + / (double) team.getValue() + ); + if(best < cur) { + best = cur; + best_team = team.getKey(); + } + } + return best_team; + } +}; diff --git a/src/test/java/ru/urfu/MapperTest.java b/src/test/java/ru/urfu/MapperTest.java new file mode 100644 index 0000000..13c15c7 --- /dev/null +++ b/src/test/java/ru/urfu/MapperTest.java @@ -0,0 +1,67 @@ +package test.java.ru.urfu; + +import ru.urfu.model.Player; +import ru.urfu.model.Position; +import ru.urfu.io.GraphDrawer; + +import org.junit.jupiter.api.Test; +import static org.junit.jupiter.api.Assertions.*; + +import java.util.Collections; +import java.util.List; +import java.util.Map; + +public class MapperTest { + @Test + static void testFirst() { + List players = List.of( + new Player("Player A", "Team A", "City A", Position.MIDFIELD, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0), + new Player("Player A", "Team A", "City A", Position.MIDFIELD, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0), + new Player("Player A", "Team A", "City A", Position.GOALKEEPER, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0), + new Player("Player A", "Team A", "City A", Position.GOALKEEPER, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0), + new Player("Player A", "Team A", "City A", Position.GOALKEEPER, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0), + new Player("Player A", "Team A", "City A", Position.DEFENDER, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0), + new Player("Player A", "Team A", "City A", Position.DEFENDER, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0) + ); + + Map playersByPosition = GraphDrawer.prepareData(players); + + assertEquals(2, playersByPosition.get(Position.MIDFIELD)); + assertEquals(3, playersByPosition.get(Position.GOALKEEPER)); + assertEquals(2, playersByPosition.get(Position.DEFENDER)); + assertEquals(0, playersByPosition.get(Position.FORWARD)); + } + + @Test + static void testSecond() { + List players = List.of( + new Player("Player A", "Team A", "City A", Position.MIDFIELD, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0), + new Player("Player A", "Team A", "City A", Position.MIDFIELD, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0), + new Player("Player A", "Team A", "City A", Position.GOALKEEPER, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0), + new Player("Player A", "Team A", "City A", Position.GOALKEEPER, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0), + new Player("Player A", "Team A", "City A", Position.GOALKEEPER, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0), + new Player("Player A", "Team A", "City A", Position.DEFENDER, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0), + new Player("Player A", "Team A", "City A", Position.DEFENDER, "Nat A", "Agency A", 0, 0, 0, 0, 0, 0) + ); + + Map playersByPosition = GraphDrawer.prepareData(players); + + assertEquals(2, playersByPosition.get(Position.MIDFIELD)); + assertEquals(3, playersByPosition.get(Position.GOALKEEPER)); + assertEquals(2, playersByPosition.get(Position.DEFENDER)); + assertEquals(0, playersByPosition.get(Position.FORWARD)); + } + + @Test + static void testThird() { + List players = Collections.emptyList(); + + Map playersByPosition = GraphDrawer.prepareData(players); + + assertEquals(4, playersByPosition.size()); + assertEquals(0, playersByPosition.get(Position.MIDFIELD)); + assertEquals(0, playersByPosition.get(Position.GOALKEEPER)); + assertEquals(0, playersByPosition.get(Position.DEFENDER)); + assertEquals(0, playersByPosition.get(Position.FORWARD)); + } +}