无法按 createdAt 对项目进行排序
Can't sort items by createdAt
我正在关注 this tutorial 一个电子商务网站并应用排序功能。
我已经将我的代码与源代码进行了比较,我认为教程使用的方法没有区别,所以我现在有点困惑。
这里是导师的source code
问题描述:
按 price
字段升序和降序对产品进行排序。但不知何故,它 无法 按 createdAt
字段对 latest
和 oldest
产品进行排序。
如果我做 console.log(a.createdAt - b.createdAt)
,它会 return NaN
.
- 在 MongoDB 中,所有项目都有
createdAt
和 price
字段。
- 如果我在
a.createdAt
或 b.createdAt
上进行控制台登录,它 return 的 createdAt
结果与项目中的一样。
- 如果我 console.log(filteredProducts),它 return 包含相同 5 个项目的所有 5 个对象。
-> 问题:在这种情况下,我们将如何解决这个问题,或者是否有更好的方法根据创建日期对项目进行排序?
下面是我的代码:
产品架构
const mongoose = require('mongoose')
const ProductSchema = new mongoose.Schema(
{
title: {
type: String,
required: true,
},
desc: {
type: String,
required: true,
},
img: {
type: String,
required: true,
},
categories: {
type: Array,
required: true,
},
size: {
type: Array,
},
color: {
type: Array,
},
price: {
type: Number,
required: true,
},
inStock: {
type: Boolean,
default: true
}
},
{ timestamps: true }
)
module.exports = mongoose.model("Product", ProductSchema)
Products.js
const Products = ({ category, filters, sort }) => {
const [products, setProducts] = useState([])
const [filteredProducts, setFilteredProducts] = useState([])
useEffect(() => {
category && setFilteredProducts(
products.filter(item =>
Object.entries(filters).every(([key, value]) =>
item[key].includes(value)
)
)
)
}, [category, filters, products])
// Sorting:
useEffect(() => {
// Sort by latest date:
if (sort === "latest") {
setFilteredProducts(prev =>
[...prev].sort((a, b) =>
a.createdAt - b.createdAt
// console.log(a.createdAt - b.createdAt) -> This returns "NaN"
)
)
} else if (sort === "asc") {
setFilteredProducts(prev =>
[...prev].sort((a, b) => a.price - b.price)
)
} else if (sort === "desc") {
setFilteredProducts(prev =>
[...prev].sort((a, b) => b.price - a.price)
)
} else {
// Sort by oldest date:
setFilteredProducts(prev =>
[...prev].sort((a, b) => b.createdAt - a.createdAt)
)
}
}, [sort])
return (
<Container>
<Title>Popular In Store</Title>
<ProductsWrapper>
{filteredProducts.map(item => (
<Product key={item.id} item={item} />
))}
</ProductsWrapper>
</Container>
);
}
createdAt
属性 是一个 non-number-like 字符串,因此尝试对它们进行算术运算将导致 NaN
.
console.log("2022-04-03T07:55:18.556Z" - "2022-04-12T07:55:18.556Z"); // NaN
使用 String.prototype.localeCompare()
在排序比较器中比较字符串值。
console.log("2022-04-03T07:55:18.556Z".localeCompare("2022-04-12T07:55:18.556Z")); // -1
示例:
// Sorting:
useEffect(() => {
// Sort by latest date:
if (sort === "latest") {
setFilteredProducts(prev =>
[...prev].sort((a, b) => a.createdAt.localeCompare(b.createdAt)
))
} else if (sort === "asc") {
setFilteredProducts(prev =>
[...prev].sort((a, b) => a.price - b.price)
)
} else if (sort === "desc") {
setFilteredProducts(prev =>
[...prev].sort((a, b) => b.price - a.price)
)
} else {
// Sort by oldest date:
setFilteredProducts(prev =>
[...prev].sort((a, b) => b.createdAt.localeCompare(a.createdAt))
)
}
}, [sort]);
请注意,这仅在日期字符串按单位大小的降序使用单位时有效,即年、月、日等...因此请确保您的日期符合此要求。如果这不切实际,那么您将需要求助于将日期字符串处理为 DateTime 对象并使用其他比较方法。
console.log(new Date("2022-04-03T07:55:18.556Z") - new Date("2022-04-12T07:55:18.556Z")); // -777600000
我正在关注 this tutorial 一个电子商务网站并应用排序功能。
我已经将我的代码与源代码进行了比较,我认为教程使用的方法没有区别,所以我现在有点困惑。
这里是导师的source code
问题描述:
按
price
字段升序和降序对产品进行排序。但不知何故,它 无法 按createdAt
字段对latest
和oldest
产品进行排序。如果我做
console.log(a.createdAt - b.createdAt)
,它会 returnNaN
.
- 在 MongoDB 中,所有项目都有
createdAt
和price
字段。
- 如果我在
a.createdAt
或b.createdAt
上进行控制台登录,它 return 的createdAt
结果与项目中的一样。
- 如果我 console.log(filteredProducts),它 return 包含相同 5 个项目的所有 5 个对象。
-> 问题:在这种情况下,我们将如何解决这个问题,或者是否有更好的方法根据创建日期对项目进行排序?
下面是我的代码:
产品架构
const mongoose = require('mongoose')
const ProductSchema = new mongoose.Schema(
{
title: {
type: String,
required: true,
},
desc: {
type: String,
required: true,
},
img: {
type: String,
required: true,
},
categories: {
type: Array,
required: true,
},
size: {
type: Array,
},
color: {
type: Array,
},
price: {
type: Number,
required: true,
},
inStock: {
type: Boolean,
default: true
}
},
{ timestamps: true }
)
module.exports = mongoose.model("Product", ProductSchema)
Products.js
const Products = ({ category, filters, sort }) => {
const [products, setProducts] = useState([])
const [filteredProducts, setFilteredProducts] = useState([])
useEffect(() => {
category && setFilteredProducts(
products.filter(item =>
Object.entries(filters).every(([key, value]) =>
item[key].includes(value)
)
)
)
}, [category, filters, products])
// Sorting:
useEffect(() => {
// Sort by latest date:
if (sort === "latest") {
setFilteredProducts(prev =>
[...prev].sort((a, b) =>
a.createdAt - b.createdAt
// console.log(a.createdAt - b.createdAt) -> This returns "NaN"
)
)
} else if (sort === "asc") {
setFilteredProducts(prev =>
[...prev].sort((a, b) => a.price - b.price)
)
} else if (sort === "desc") {
setFilteredProducts(prev =>
[...prev].sort((a, b) => b.price - a.price)
)
} else {
// Sort by oldest date:
setFilteredProducts(prev =>
[...prev].sort((a, b) => b.createdAt - a.createdAt)
)
}
}, [sort])
return (
<Container>
<Title>Popular In Store</Title>
<ProductsWrapper>
{filteredProducts.map(item => (
<Product key={item.id} item={item} />
))}
</ProductsWrapper>
</Container>
);
}
createdAt
属性 是一个 non-number-like 字符串,因此尝试对它们进行算术运算将导致 NaN
.
console.log("2022-04-03T07:55:18.556Z" - "2022-04-12T07:55:18.556Z"); // NaN
使用 String.prototype.localeCompare()
在排序比较器中比较字符串值。
console.log("2022-04-03T07:55:18.556Z".localeCompare("2022-04-12T07:55:18.556Z")); // -1
示例:
// Sorting:
useEffect(() => {
// Sort by latest date:
if (sort === "latest") {
setFilteredProducts(prev =>
[...prev].sort((a, b) => a.createdAt.localeCompare(b.createdAt)
))
} else if (sort === "asc") {
setFilteredProducts(prev =>
[...prev].sort((a, b) => a.price - b.price)
)
} else if (sort === "desc") {
setFilteredProducts(prev =>
[...prev].sort((a, b) => b.price - a.price)
)
} else {
// Sort by oldest date:
setFilteredProducts(prev =>
[...prev].sort((a, b) => b.createdAt.localeCompare(a.createdAt))
)
}
}, [sort]);
请注意,这仅在日期字符串按单位大小的降序使用单位时有效,即年、月、日等...因此请确保您的日期符合此要求。如果这不切实际,那么您将需要求助于将日期字符串处理为 DateTime 对象并使用其他比较方法。
console.log(new Date("2022-04-03T07:55:18.556Z") - new Date("2022-04-12T07:55:18.556Z")); // -777600000