var range = getDates(new Date(), new Date().addDays(7));
Chciałbym, aby „zakres” był tablicą obiektów dat, po jednym na każdy dzień między dwiema datami.
Sztuczka polega na tym, że powinien również obsługiwać granice miesięcy i lat.
var range = getDates(new Date(), new Date().addDays(7));
Chciałbym, aby „zakres” był tablicą obiektów dat, po jednym na każdy dzień między dwiema datami.
Sztuczka polega na tym, że powinien również obsługiwać granice miesięcy i lat.
Odpowiedzi:
Date.prototype.addDays = function(days) {
var date = new Date(this.valueOf());
date.setDate(date.getDate() + days);
return date;
}
function getDates(startDate, stopDate) {
var dateArray = new Array();
var currentDate = startDate;
while (currentDate <= stopDate) {
dateArray.push(new Date (currentDate));
currentDate = currentDate.addDays(1);
}
return dateArray;
}
Oto funkcjonalne demo http://jsfiddle.net/jfhartsock/cM3ZU/
startDate
i endDate
? Ponieważ jeśli startDate
czas jest późniejszy niż stopDate
czas, to nie zostanie uwzględniony stopDate
w wyniku, prawda?
Spróbuj tego, pamiętaj, aby uwzględnić moment js,
function getDates(startDate, stopDate) {
var dateArray = [];
var currentDate = moment(startDate);
var stopDate = moment(stopDate);
while (currentDate <= stopDate) {
dateArray.push( moment(currentDate).format('YYYY-MM-DD') )
currentDate = moment(currentDate).add(1, 'days');
}
return dateArray;
}
var dateArray = [];
Szczegóły tutaj
var currentDate = moment(startDate);
jeśli używasz tej metody dwa razy w tej samej dacie moment.js, zdziwisz się, dlaczego działa ona po raz pierwszy. Dzieje się tak, ponieważ javascripts przekazuje obiekty przez referencję, więc funkcja kończy się dwukrotnym użyciem startDate (która jest już zmutowana). Poprawienie powyższej poprawki zapewnia, że pracujesz z nowymi i unikalnymi obiektami moment js w zakresie funkcji. Sprawdź to skrzypce
Spojrzałem na wszystkie powyżej. Skończyło się na pisaniu siebie. Nie potrzebujesz do tego momentów . Natywna pętla for jest wystarczająca i ma największy sens, ponieważ istnieje pętla for do zliczania wartości w zakresie.
Jedna wkładka:
var getDaysArray = function(s,e) {for(var a=[],d=new Date(s);d<=e;d.setDate(d.getDate()+1)){ a.push(new Date(d));}return a;};
Długa wersja
var getDaysArray = function(start, end) {
for(var arr=[],dt=new Date(start); dt<=end; dt.setDate(dt.getDate()+1)){
arr.push(new Date(dt));
}
return arr;
};
Podaj daty pomiędzy:
var daylist = getDaysArray(new Date("2018-05-01"),new Date("2018-07-01"));
daylist.map((v)=>v.toISOString().slice(0,10)).join("")
/*
Output:
"2018-05-01
2018-05-02
2018-05-03
...
2018-06-30
2018-07-01"
*/
Dni od minionej daty do teraz:
var daylist = getDaysArray(new Date("2018-05-01"),new Date());
daylist.map((v)=>v.toISOString().slice(0,10)).join("")
getDaysArray
? Nie dni między nimi.
for (var arr=[], dt=new Date(start), ...)
. ;-)
Używam moment.js i Twix.js, które zapewniają bardzo dobre wsparcie dla manpulacji daty i czasu
var itr = moment.twix(new Date('2012-01-15'),new Date('2012-01-20')).iterate("days");
var range=[];
while(itr.hasNext()){
range.push(itr.next().toDate())
}
console.log(range);
Mam to uruchomione na http://jsfiddle.net/Lkzg1bxb/
var boxingDay = new Date("12/26/2010");
var nextWeek = boxingDay*1 + 7*24*3600*1000;
function getDates( d1, d2 ){
var oneDay = 24*3600*1000;
for (var d=[],ms=d1*1,last=d2*1;ms<last;ms+=oneDay){
d.push( new Date(ms) );
}
return d;
}
getDates( boxingDay, nextWeek ).join("\n");
// Sun Dec 26 2010 00:00:00 GMT-0700 (Mountain Standard Time)
// Mon Dec 27 2010 00:00:00 GMT-0700 (Mountain Standard Time)
// Tue Dec 28 2010 00:00:00 GMT-0700 (Mountain Standard Time)
// Wed Dec 29 2010 00:00:00 GMT-0700 (Mountain Standard Time)
// Thu Dec 30 2010 00:00:00 GMT-0700 (Mountain Standard Time)
// Fri Dec 31 2010 00:00:00 GMT-0700 (Mountain Standard Time)
// Sat Jan 01 2011 00:00:00 GMT-0700 (Mountain Standard Time)
function (startDate, endDate, addFn, interval) {
addFn = addFn || Date.prototype.addDays;
interval = interval || 1;
var retVal = [];
var current = new Date(startDate);
while (current <= endDate) {
retVal.push(new Date(current));
current = addFn.call(current, interval);
}
return retVal;
}
Jeśli używasz momentu, możesz użyć ich „oficjalnej wtyczki” do określania zakresów moment-range
i wtedy staje się to trywialne.
przykład węzła moment-zakres:
const Moment = require('moment');
const MomentRange = require('moment-range');
const moment = MomentRange.extendMoment(Moment);
const start = new Date("11/30/2018"), end = new Date("09/30/2019")
const range = moment.range(moment(start), moment(end));
console.log(Array.from(range.by('day')))
Przykład przeglądarki zakresu momentu:
window['moment-range'].extendMoment(moment);
const start = new Date("11/30/2018"), end = new Date("09/30/2019")
const range = moment.range(moment(start), moment(end));
console.log(Array.from(range.by('day')))
<script src="https://cdnjs.cloudflare.com/ajax/libs/moment.js/2.22.2/moment.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/moment-range/4.0.1/moment-range.js"></script>
przykład daty fns:
Jeśli używasz, date-fns
to eachDay
jest twoim przyjacielem i otrzymujesz zdecydowanie najkrótszą i najbardziej zwięzłą odpowiedź:
console.log(dateFns.eachDay(
new Date(2018, 11, 30),
new Date(2019, 30, 09)
))
<script src="https://cdnjs.cloudflare.com/ajax/libs/date-fns/1.29.0/date_fns.min.js"></script>
Właśnie natknąłem się na to pytanie, najłatwiej to zrobić za pomocą momentu:
Najpierw musisz zainstalować moment i zakres momentu:
const Moment = require('moment');
const MomentRange = require('moment-range');
const moment = MomentRange.extendMoment(Moment);
const start = moment()
const end = moment().add(2, 'months')
const range = moment.range(start, end)
const arrayOfDates = Array.from(range.by('days'))
console.log(arrayOfDates)
Od jakiegoś czasu korzystam z rozwiązania @Mohammed Safeer i wprowadziłem kilka ulepszeń. Używanie sformatowanych dat jest złą praktyką podczas pracy w kontrolerach. moment().format()
powinny być używane tylko do celów wyświetlania w widokach. Pamiętaj również, że moment().clone()
zapewnia to oddzielenie od parametrów wejściowych, co oznacza, że daty wejściowe nie są zmieniane. Gorąco zachęcam do korzystania z moment.js podczas pracy z datami.
Stosowanie:
startDate
, endDate
parametryinterval
parametr jest opcjonalny i ma wartość domyślną „dni”. Użyj interwałów wspieranych przez .add()
metodę (moment.js). Więcej szczegółów tutajtotal
parametr jest przydatny podczas określania interwałów w minutach. Domyślnie 1.Odwołać się:
var startDate = moment(),
endDate = moment().add(1, 'days');
getDatesRangeArray(startDate, endDate, 'minutes', 30);
Funkcjonować:
var getDatesRangeArray = function (startDate, endDate, interval, total) {
var config = {
interval: interval || 'days',
total: total || 1
},
dateArray = [],
currentDate = startDate.clone();
while (currentDate < endDate) {
dateArray.push(currentDate);
currentDate = currentDate.clone().add(config.total, config.interval);
}
return dateArray;
};
Używając ES6 masz Array. od co oznacza, że możesz napisać naprawdę elegancką funkcję, która pozwala na dynamiczne interwały (godziny, dni, miesiące).
function getDates(startDate, endDate, interval) {
const duration = endDate - startDate;
const steps = duration / interval;
return Array.from({length: steps+1}, (v,i) => new Date(startDate.valueOf() + (interval * i)));
}
const startDate = new Date(2017,12,30);
const endDate = new Date(2018,1,3);
const dayInterval = 1000 * 60 * 60 * 24; // 1 day
const halfDayInterval = 1000 * 60 * 60 * 12; // 1/2 day
console.log("Days", getDates(startDate, endDate, dayInterval));
console.log("Half Days", getDates(startDate, endDate, halfDayInterval));
new Date(2017,12,30)
jest 30 stycznia 2018 r., dla mnie zakres dat zaczyna się 29 stycznia 2018 r. Nie wszystkie dni mają długość 8,64e7 ms (24 godziny), w których obserwuje się czas letni. ;-)
Niedawno pracowałem z moment.js, podążając za rozwiązaniami ..
function getDateRange(startDate, endDate, dateFormat) {
var dates = [],
end = moment(endDate),
diff = endDate.diff(startDate, 'days');
if(!startDate.isValid() || !endDate.isValid() || diff <= 0) {
return;
}
for(var i = 0; i < diff; i++) {
dates.push(end.subtract(1,'d').format(dateFormat));
}
return dates;
};
console.log(getDateRange(startDate, endDate, dateFormat));
Wynik byłby:
["09/03/2015", "10/03/2015", "11/03/2015", "12/03/2015", "13/03/2015", "14/03/2015", "15/03/2015", "16/03/2015", "17/03/2015", "18/03/2015"]
var listDate = [];
var startDate ='2017-02-01';
var endDate = '2017-02-10';
var dateMove = new Date(startDate);
var strDate = startDate;
while (strDate < endDate){
var strDate = dateMove.toISOString().slice(0,10);
listDate.push(strDate);
dateMove.setDate(dateMove.getDate()+1);
};
console.log(listDate);
//["2017-02-01", "2017-02-02", "2017-02-03", "2017-02-04", "2017-02-05", "2017-02-06", "2017-02-07", "2017-02-08", "2017-02-09", "2017-02-10"]
var
wcześniej strDate
wewnątrz pętli while!
d3js zapewnia wiele przydatnych funkcji i zawiera d3.time do łatwej manipulacji datami
Na specjalne życzenie:
Utc
var range = d3.utcDay.range(new Date(), d3.utcDay.offset(new Date(), 7));
lub czasu lokalnego
var range = d3.timeDay.range(new Date(), d3.timeDay.offset(new Date(), 7));
zakres będzie tablicą obiektów dat, które przypadają na pierwszą możliwą wartość każdego dnia
Możesz zmienić czas z dnia na godzinę, godzinę, miesiąc itp., aby uzyskać te same wyniki w różnych odstępach czasu
Oto jedna linijka, która nie wymaga żadnych bibliotek na wypadek, gdybyś nie chciał tworzyć innej funkcji. Po prostu zastąp startDate (w dwóch miejscach) i endDate (które są obiektami daty js) zmiennymi lub wartościami dat. Oczywiście, jeśli wolisz, możesz umieścić go w funkcji
Array(Math.floor((endDate - startDate) / 86400000) + 1).fill().map((_, idx) => (new Date(startDate.getTime() + idx * 86400000)))
Używam tej funkcji
function getDatesRange(startDate, stopDate) {
const ONE_DAY = 24*3600*1000;
var days= [];
var currentDate = new Date(startDate);
while (currentDate <= stopDate) {
days.push(new Date (currentDate));
currentDate = currentDate - 1 + 1 + ONE_DAY;
}
return days;
}
Używam prostej pętli while do obliczania dat między datami
var start = new Date("01/05/2017");
var end = new Date("06/30/2017");
var newend = end.setDate(end.getDate()+1);
end = new Date(newend);
while(start < end){
console.log(new Date(start).getTime() / 1000); // unix timestamp format
console.log(start); // ISO Date format
var newDate = start.setDate(start.getDate() + 1);
start = new Date(newDate);
}
Uwaga: zdaję sobie sprawę, że jest to nieco inne niż żądane rozwiązanie, ale myślę, że wielu uzna to za przydatne.
Jeśli chcesz znaleźć każdy interwał „x” (dni, miesiące, lata itd.) Między dwiema datami, momentem.js i zakresem chwil pakiety rozszerzenia włącz tę funkcję.
Na przykład, aby znaleźć każdy 30 dzień między dwiema datami :
window['moment-range'].extendMoment(moment);
var dateString = "2018-05-12 17:32:34.874-08";
var start = new Date(dateString);
var end = new Date();
var range1 = moment.range(start, end);
var arrayOfIntervalDates = Array.from(range1.by('day', { step: 30 }));
arrayOfIntervalDates.map(function(intervalDate){
console.log(intervalDate.format('YY-M-DD'))
});
Wygeneruj tablicę lat:
const DAYS = () => {
const days = []
const dateStart = moment()
const dateEnd = moment().add(30, ‘days')
while (dateEnd.diff(dateStart, ‘days') >= 0) {
days.push(dateStart.format(‘D'))
dateStart.add(1, ‘days')
}
return days
}
console.log(DAYS())
Wygeneruj tablice na miesiąc:
const MONTHS = () => {
const months = []
const dateStart = moment()
const dateEnd = moment().add(12, ‘month')
while (dateEnd.diff(dateStart, ‘months') >= 0) {
months.push(dateStart.format(‘M'))
dateStart.add(1, ‘month')
}
return months
}
console.log(MONTHS())
Wygeneruj tablice na dni:
const DAYS = () => {
const days = []
const dateStart = moment()
const dateEnd = moment().add(30, ‘days')
while (dateEnd.diff(dateStart, ‘days') >= 0) {
days.push(dateStart.format(‘D'))
dateStart.add(1, ‘days')
}
return days
}
console.log(DAYS())
Możesz to łatwo zrobić za pomocą momentJS
Dodaj chwilę do swoich zależności
npm i moment
Następnie zaimportuj to do swojego pliku
var moment = require("moment");
Następnie użyj poniższego kodu, aby uzyskać listę wszystkich dat między dwiema datami
let dates = [];
let currDate = moment.utc(new Date("06/30/2019")).startOf("day");
let lastDate = moment.utc(new Date("07/30/2019")).startOf("day");
do {
dates.push(currDate.clone().toDate());
} while (currDate.add(1, "days").diff(lastDate) < 0);
dates.push(currDate.clone().toDate());
console.log(dates);
To może komuś pomóc,
Możesz z tego pobrać dane wyjściowe wiersza i sformatować obiekt row_date, jak chcesz.
var from_date = '2016-01-01';
var to_date = '2016-02-20';
var dates = getDates(from_date, to_date);
console.log(dates);
function getDates(from_date, to_date) {
var current_date = new Date(from_date);
var end_date = new Date(to_date);
var getTimeDiff = Math.abs(current_date.getTime() - end_date.getTime());
var date_range = Math.ceil(getTimeDiff / (1000 * 3600 * 24)) + 1 ;
var weekday = ["SUN", "MON", "TUE", "WED", "THU", "FRI", "SAT"];
var months = ["JAN", "FEB", "MAR", "APR", "MAY", "JUN", "JUL", "AUG", "SEP", "OCT", "NOV", "DEC"];
var dates = new Array();
for (var i = 0; i <= date_range; i++) {
var getDate, getMonth = '';
if(current_date.getDate() < 10) { getDate = ('0'+ current_date.getDate());}
else{getDate = current_date.getDate();}
if(current_date.getMonth() < 9) { getMonth = ('0'+ (current_date.getMonth()+1));}
else{getMonth = current_date.getMonth();}
var row_date = {day: getDate, month: getMonth, year: current_date.getFullYear()};
var fmt_date = {weekDay: weekday[current_date.getDay()], date: getDate, month: months[current_date.getMonth()]};
var is_weekend = false;
if (current_date.getDay() == 0 || current_date.getDay() == 6) {
is_weekend = true;
}
dates.push({row_date: row_date, fmt_date: fmt_date, is_weekend: is_weekend});
current_date.setDate(current_date.getDate() + 1);
}
return dates;
}
https://gist.github.com/pranid/3c78f36253cbbc6a41a859c5d718f362.js
Oto gotowa metoda, która zaakceptuje daty lub ciągi znaków lub ich mieszaninę jako dane wejściowe i wygeneruje tablicę dat jako daty Moment. Jeśli nie chcesz, aby daty Moment były danymi wyjściowymi, zmień to, co map()
zwraca metoda.
const moment = require('moment');
// ...
/**
* @param {string|import('moment').Moment} start
* @param {string|import('moment').Moment} end
* @returns {import('moment').Moment[]}
*/
const getDateRange = (start, end) => {
const s = moment.isMoment(start) ? start : moment(start);
const e = moment.isMoment(end) ? end : moment(end);
return [...Array(1 + e.diff(s, 'days')).keys()].map(n => moment(s).add(n, 'days'));
};
@ softvar, ale z opcją daty pracy
/**
* Returns array of working days between two dates.
*
* @param {string} startDate
* The start date in yyyy-mm-dd format.
* @param {string} endDate
* The end date in yyyy-mm-dd format.
* @param {boolean} onlyWorkingDays
* If true only working days are returned. Default: false
*
* @return {array}
* Array of dates in yyyy-mm-dd string format.
*/
function getDates(startDate, stopDate, onlyWorkingDays) {
let doWd = typeof onlyWorkingDays ==='undefined' ? false : onlyWorkingDays;
let dateArray = [];
let dayNr;
let runDateObj = moment(startDate);
let stopDateObj = moment(stopDate);
while (runDateObj <= stopDateObj) {
dayNr = runDateObj.day();
if (!doWd || (dayNr>0 && dayNr<6)) {
dateArray.push(moment(runDateObj).format('YYYY-MM-DD'));
}
runDateObj = moment(runDateObj).add(1, 'days');
}
return dateArray;
}
Funkcjonować:
var dates = [],
currentDate = startDate,
addDays = function(days) {
var date = new Date(this.valueOf());
date.setDate(date.getDate() + days);
return date;
};
while (currentDate <= endDate) {
dates.push(currentDate);
currentDate = addDays.call(currentDate, 1);
}
return dates;
};
Stosowanie:
var dates = getDatesRange(new Date(2019,01,01), new Date(2019,01,25));
dates.forEach(function(date) {
console.log(date);
});
Mam nadzieję, że ci to pomoże