I have following csv
file:
OF_DEPARTURE_COORDINATE_Y,OF_ARRIVAL_COUNTRY,OF_ARRLV2,OF_ARRLV1,OF_ARRLV0,OF_ARRIVAL_CITY,OF_ARRIVAL_ZIPCODE,OF_ARRIVAL_COORDINATE_X,OF_ARRIVAL_COORDINATE_Y,OF_WEIGHT,OF_VOLUME,OF_LENGTH,OF_GOODS_KND,OF_TAIL_LIFT,OF_PALLETS_EXCHANGE,OF_NB_PALLETS
D,SN,1,,DRESDEN,01067,1372931,5105325,A,3,SB,57,ZELL AM SEE,5700,1279591,4732422,2500,0,36,MG,N,N,0
D,HE,35,,HAIGER,35708,820051,5074357,RO,2,,,ORADEA,410000,2193891,4705371,100,1,0,MG,N,N,0
F,NP,62,,ANVIN,62134,225617,5044640,F,BR,29,,QUIMPER,29000,-410790,4799464,10000,0,50,MG,N,N,0
I need to check how many times arrival and departure countries are mentioned there. And use for this functional approach. CSV file has only country codes. All countries are stored at predefined enum.
My solution works iteratively definitely, I am sure that it can be implemented with streams. I tried to play with collect()
& groupingBy()
but without success.
Here is iterative solution (result is stored to map with country for key - number of occurrences of values):
public class CountryCounter {
private static Map<Country, Long> countryMap = Country.getCountryMap();
public static void main(String[] args) {
processPath(FileLocation.SEARCHES_REG);
printMap();
}
private static void printMap() {
Map<Country, Long> reversedMap = new TreeMap<>(countryMap);
Map<Country, Long> result = new LinkedHashMap<>();
reversedMap.entrySet().stream()
.sorted(Map.Entry.<Country, Long>comparingByValue().reversed())
.forEachOrdered(x -> result.put(x.getKey(), x.getValue()));
for (Map.Entry entry : result.entrySet()) {
System.out.println(entry.getKey() + ", " + entry.getValue());
}
}
private static void processPath(FileLocation filePath) {
FileLocation.printFileName(filePath);
Path path = Paths.get(".", filePath.getFilePath());
List<String> csvLines = null;
try {
csvLines = Files.readAllLines(path);
} catch (IOException e) {
e.printStackTrace();
}
for (String csvLine : csvLines) {
String[] lineArgs = csvLine.split(",");
String arrivalCntCode = lineArgs[0];
String departureCntCode = lineArgs[8];
if (arrivalCntCode == null || departureCntCode == null) {
return;
}
Country arrCountry = Country.getByCode(arrivalCntCode);
Country depCountry = Country.getByCode(departureCntCode);
if (countryMap.containsKey(arrCountry)) {
countryMap.put(arrCountry, countryMap.get(arrCountry) + 1);
}
if (countryMap.containsKey(depCountry)) {
countryMap.put(depCountry, countryMap.get(depCountry) + 1);
}
}
}
}
FileLocation
is enum for storing relative pathes for csv files.
Here you can find Country enum
It works fine:
France, 82109
Germany, 31589
Romania, 27634
Italy, 11652
Netherlands, 9190
...
How to achieve the same with Java 8
features, like streams?
We can:
Use Files.lines(path)
instead of readAllLines
to directly get the lines as a stream.
Use flatMap
to turn the lines into a stream of countries.
Group the countries counting occurrences using a downstream collector.
For example:
public Map<Country, Long> count(Path path) throws IOException {
return Files.lines(path)
.flatMap(line -> getRelevantCells(line))
.map(Country::getByCode)
.filter(Objects::nonNull)
.collect(Collectors.groupingBy(Function.identity(), Collectors.counting()));
}
private Stream<String> getRelevantCells(String line) {
String[] cells = line.split(",");
return Stream.of(cells[0], cells[8]);
}
Collected from the Internet
Please contact [email protected] to delete if infringement.
Comments