英文:
Why I can't access the itemName after I peform the price mapping in the stream?
问题
以下是翻译好的内容:
class Order{
List<Item> items = new ArrayList();
public List<Item> getItems() {
return items;
}
public void setItems(List<Item> items) {
this.items = items;
}
}
class Item{
String name;
double price;
public Item(String name, double price) {
super();
this.name = name;
this.price = price;
}
public Item() {
}
public static void main(String[] args){
Item i1 = new Item("Soap", 3.9);
Item i2 = new Item("Plate", 15.9);
Item i3 = new Item("Wok", 199.9);
Order order = new Order();
order.setItems( Arrays.asList( i1, i2, i3 ) );
List<Item> items = order.getItems();
// 在这里进行更改,以便获取商品名称
List<String> itemNames = items.stream().map(elem -> elem.name).collect(Collectors.toList());
itemNames.forEach(System.out::println);
List<Double> subTtl = items.stream().map(elem -> elem.price * 1.06).collect(Collectors.toList());
subTtl.forEach(System.out::println);
double ttl = subTtl.stream().mapToDouble(Number::doubleValue).summaryStatistics().getSum();
System.out.println("Total Payment without tax: " + ttl);
System.out.println("Total Payment: " + ttl * 1.10);
}
}
英文:
May I know does java stream allows us to access back the itemName from the subTtl list?
The reason of accessing itemName is because I want to output the data similar as below but the data will be form in the array format.
The expected output will be
like this
class Order{
List<Item> items = new ArrayList();
public List<Item> getItems() {
return items;
}
public void setItems(List<Item> items) {
this.items = items;
}
}
class Item{
String name;
double price;
public Item(String name, double price) {
super();
this.name = name;
this.price = price;
}
public Item() {
}
public static void main(String[] args){
Item i1 = new Item("Soap", 3.9);
Item i2 = new Item("Plate", 15.9);
Item i3 = new Item("Wok", 199.9);
Order order = new Order();
order.setItems( Arrays.asList( i1, i2, i3 ) );
List<Item> items = order.getItems();
List<Double> subTtl = items.stream().map(elem -> elem.price * 1.06).collect(Collectors.toList());
subTtl.forEach(System.out::println);
double ttl = subTtl.stream().mapToDouble(Number::doubleValue).summaryStatistics().getSum();
System.out.println("Total Payment without tax: " + ttl);
System.out.println("Total Payment: " + ttl * 1.10);
}
}
答案1
得分: 2
itemName
是Item
的一个成员。只有从包含Item
的流/集合中才能保证访问正确的itemName
。你可以实现你想要的,但你必须从List<Item> items
开始流式传输。然而,从列表中流式传输并执行除主要工作以外的任何其他操作都被视为“副作用”(副作用不是“纯函数”并且通常被认为不是最理想的)。
因此,最终你会得到类似这样的代码(未经测试):
items.stream().forEach(item -> System.out.println(item.getName()
+ "\t" + item.getPrice()
+ "\t" + (item.getPrice() * 0.06)
+ "\t" + (item.getPrice() * 1.06));
double grandTotal = items.stream().reduce(0, Integer::sum) * 1.06;
System.out.println("GRAND TOTAL:\t\t\t" + grandTotal);
double serviceTax = grandTotal * 0.1;
System.out.println("SERVICE TAX:\t\t\t" + serviceTax);
double totalPayment = grandTotal * 1.1;
System.out.println("TOTAL PAYMENT:\t\t\t" + totalPayment);
我已经为需要暴露的类变量添加了getter方法。我还假设布局不需要与您的图像布局完全相同 - 如果需要,您可以使用填充文本将事物正确对齐,但这可能比较费力,不过根据是否商业/作业性质,您可能希望进行修改。我还建议封装显示总金额、服务税和总付款的方法,这样您只需要调用单行函数,函数名更接近于:
displayGrandTotal(items);
displayServiceTax(items);
displayTotalPayment(items);
希望这对您有所帮助。
英文:
itemName
is a member of Item
. You could only guarantee access to the correct itemName
from a stream/collection containing Item
s. Its possible to get what you want but you'd have to start streaming from the List<Item> items
. However to stream over a list and perform anything other than one main job would be considered a "side effect" (side effects are not "pure functions" and generally considered less than ideal).
So you'd ultimately have something like (untested):
items.stream().foreach(item -> System.out.println(item.getName()
+ "\t" + item.getPrice()
+ "\t" + (item.getPrice() * 0.06)
+ "\t" + (item.getPrice() * 1.06));
double grandTotal = items.stream().reduce(0, Integer::sum) * 1.06;
System.out.println("GRAND TOTAL:\t\t\t" + grandTotal);
double serviceTax = grandTotal * 0.1;
System.out.println("SERVICE TAX:\t\t\t" + serviceTax);
double totalPayment = grandTotal * 1.1;
System.out.println("TOTAL PAYMENT:\t\t\t" + totalPayment);
I've taken the liberty to add getters for the class variables that need to be exposed. I've also assumed the layout doesn't need to be exactly the same as your image layout - for that you'd want to use padded text to line things up correctly but that will be more effort than its likely worth but you may wish to amend depending on whether this is commercial/homework. I'd also consider encapsulating the methods for displaying the grand total, service tax and total payment so you can just call a single line function whose name is more along the lines of
displayGrandTotal(items);
displayServiceTax(items);
displayTotalPayment(items);
Hopefully this is useful
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论