Reputation:
I am creating a sort of tilling system that will take into account offers on certain products. I need to create a half price offer that will display either true or false depending whether the offer has been applied.
HalfPrice Class:
class HalfPriceOffer :Offer {
init(){
super.init(name: "Half Price on Wine")
applicableProducts = [901,902];
}
override func isApplicableToList(list: [ShoppingItem]) -> Bool {
//should return true if a dicount can be applied based on the supplied list of products (i.e. a product must be matched to an offer)
return false
}
ShoppingItem Class
import Foundation
class ShoppingItem {
var name :String
var priceInPence :Int
var productId :Int
init(name:String, price:Int, productId:Int){
self.name = name
self.priceInPence = price
self.productId = productId
}
}
I know it uses loops; but I am unsure of how to actually write it. Thanks in advance :)
Upvotes: 0
Views: 913
Reputation: 5916
It's perhaps less complex to think whether the offer items are in the list rather than the list items are in the offer.
override func isApplicableToList(list: [ShoppingItem]) -> Bool {
//should return true if a discount can be applied based on the supplied list of products (i.e. a product must be matched to an offer)
let a = list.map({$0.productId})
for p in applicableProducts
{
if !a.contains(p) {return false}
}
return true
}
And here's a full working code example, which fills in the implied gaps in the sample code:
class ShoppingItem {
var name: String
var priceInPence: Int
var productId: Int
init(name:String, price:Int, productId:Int){
self.name = name
self.priceInPence = price
self.productId = productId
}
}
class Offer {
var applicableProducts = [Int]()
var name:String
init(name: String) {
self.name = name
}
func isApplicableToList(list: [ShoppingItem]) -> Bool {
return false
}
}
class HalfPriceOffer: Offer {
init(){
super.init(name: "Half Price on Wine")
applicableProducts = [901,902]
}
override func isApplicableToList(list: [ShoppingItem]) -> Bool {
//should return true if a discount can be applied based on the supplied list of products (i.e. a product must be matched to an offer)
let a = list.map({$0.productId})
for p in applicableProducts
{
if !a.contains(p) {return false}
}
return true
}
}
let a = [ShoppingItem(name: "one", price: 1000, productId: 901), ShoppingItem(name: "two", price: 1009, productId: 907),ShoppingItem(name: "three", price: 1084, productId: 902)]
HalfPriceOffer().isApplicableToList(a) // true
let b = [ShoppingItem(name: "one", price: 1000, productId: 901), ShoppingItem(name: "two", price: 1009, productId: 907)]
HalfPriceOffer().isApplicableToList(b) // false
Upvotes: 0
Reputation: 2298
You could use the reduce function to achieve this:
func isApplicableToList(list: [ShoppingItem]) -> Bool {
return list.reduce(false) { (initial: Bool, current: ShoppingItem) -> Bool in
return initial || applicableProducts.contains(current.productId)
}
}
You can even write this shorter (Swift is awesome):
func isApplicableToList(list: [ShoppingItem]) -> Bool {
return list.reduce(false) { $0 || applicableProducts.contains($1.productId) }
}
Upvotes: 1