简体   繁体   中英

Query Guava Table by Value

I am creating a Table from a CSV file with data consisting of user ratings for different items dataset

I use the following code to fill the Table

 Reader in = new FileReader(OriginalRatingDataPath); Iterable<CSVRecord> records = CSVFormat.EXCEL.withHeader().parse(in); Table<Integer,Integer,Integer> ratings = HashBasedTable.create(); for (CSVRecord record : records) { ratings.put(Integer.parseInt(record.get("userID")),Integer.parseInt(record.get("itemID")),Integer.parseInt(record.get("rating"))); }

How do I query the table to get users who have rated items 3 to 5?

Option 1

The point of a table is to allow you to access records by either Row or Column. So if you need to access by rating, the easiest method is to use rating as a column.

Reader in = new FileReader(OriginalRatingDataPath);
Iterable<CSVRecord> records = CSVFormat.EXCEL.withHeader().parse(in);

Table<Integer,Integer,Integer> ratings = HashBasedTable.create();
for (CSVRecord record : records) {
    ratings.put(Integer.parseInt(record.get("userID")), Integer.parseInt(record.get("rating")), Integer.parseInt(record.get("itemID")));
}

// Copy column 3 to a new map to prevent editing the table itself
// when adding columns 4 and 5 - in turn preventing a memory leak
// from indirectly holding onto `ratings` through the map
Map<Integer, Integer> usersToItemId = new HashMap<>(ratings.column(3));
usersToItemId.putAll(ratings.column(4));
usersToItemId.putAll(ratings.column(5));

// To get just User IDs
Set<Integer> userIds = usersToItemId.keySet();

Option 2

If the majority of your operations are going to be accessing the table by itemID and userID you may not want to make rating the column. In that case, you can use the cellSet method and manually iterate the table. It's performance won't be as good but it will work.

// Your current code

Set<Integer> userIds = new HashSet<>();
for (Table.Cell<Integer, Integer, Integer> cell : ratings.cellSet()) {
    if (3 <= cell.getValue() && cell.getValue() <= 5) {
        userIds.add(cell.getRowKey());
    }
}

Stream via cellSet()

private String getRowKeyByValue(String value)
{
    return records.cellSet()
            .stream()
            .filter(cell -> cell.getValue().equals(value))
            .map(Table.Cell::getRowKey)
            .findFirst()
            .orElse(null);
}

private String getColumnKeyByValue(String value)
{
    return records.cellSet()
            .stream()
            .filter(cell -> cell.getValue().equals(value))
            .map(Table.Cell::getColumnKey)
            .findFirst()
            .orElse(null);
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM