var range = getDates(new Date(), new Date().addDays(7));
"Aralık" ın iki tarih arasındaki her gün için bir tarih nesneleri dizisi olmasını istiyorum.
İşin püf noktası, ay ve yıl sınırlarını da ele alması gerektiğidir.
var range = getDates(new Date(), new Date().addDays(7));
"Aralık" ın iki tarih arasındaki her gün için bir tarih nesneleri dizisi olmasını istiyorum.
İşin püf noktası, ay ve yıl sınırlarını da ele alması gerektiğidir.
Yanıtlar:
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;
}
İşte işlevsel bir demo http://jsfiddle.net/jfhartsock/cM3ZU/
startDate
ve öğesinden ayırmalı mıyız endDate
? Çünkü eğer startDate
zaman, zamandan daha sonraysa sonuca stopDate
dahil olmaz stopDate
, değil mi?
Yukarıdakilerin tümüne baktım. Kendimi yazmayı bıraktım. Bunun için momentj'lere ihtiyacınız yok . Yerel bir for döngüsü yeterlidir ve en mantıklıdır çünkü bir aralıktaki değerleri saymak için bir for döngüsü vardır.
Bir Astar:
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;};
Uzun versiyon
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;
};
Aradaki tarihleri listeleyin:
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"
*/
Geçmiş bir tarihten bugüne kadar geçen günler:
var daylist = getDaysArray(new Date("2018-05-01"),new Date());
daylist.map((v)=>v.toISOString().slice(0,10)).join("")
getDaysArray
? Aradaki günler değil.
for (var arr=[], dt=new Date(start), ...)
. ;-)
Bunu deneyin, js anını eklemeyi unutmayın,
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 = [];
Ayrıntılar burada
var currentDate = moment(startDate);
Bu yöntemi aynı moment.js tarihlerinde iki kez kullanıyorsanız, neden sadece ilk seferinde çalıştığını şaşıracaksınız. Bunun nedeni, javascripts nesneleri başvuruya göre iletmesidir, böylece işlev startDate'i iki kez kullanır (ki bu zaten mutasyona uğramıştır). Yukarıdaki düzeltmeye yama uygulamak, işlev kapsamındaki yeni ve benzersiz moment js nesneleriyle çalışmanızı sağlar. Bu kemanı
Moment.js ve Twix.js kullanıyorum , tarih ve saat yönetimi için çok büyük destek sağlıyorlar
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);
Bunu http://jsfiddle.net/Lkzg1bxb/ adresinde çalıştırıyorum
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;
}
Moment kullanıyorsanız, aralıklar için onların "resmi eklentisini" kullanabilirsiniz moment-range
ve sonra bu önemsiz hale gelir.
moment aralığı düğüm örneği:
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')))
moment aralığı tarayıcı örneği:
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>
tarih fns örneği:
Eğer kullanıyorsanız, date-fns
o zaman eachDay
arkadaşınızdır ve en kısa ve en özlü cevabı alırsınız:
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>
Şu soruyla şimdi karşılaştım, bunu yapmanın en kolay yolu anı kullanmak:
Önce moment ve moment aralığını yüklemeniz gerekir:
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)
ES6'yı kullanarak Array.from'a sahipsiniz, yani dinamik Aralıklara (saatler, günler, aylar) izin veren gerçekten zarif bir işlev yazabilirsiniz.
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)
30 Ocak 2018, benim için tarih aralığı 29 Ocak 2018'de başlıyor. Yaz saati uygulamasının gözlemlendiği tüm günler 8.64e7 ms (24 saat) uzunluğunda değildir. ;-)
Geçenlerde moment.js ile çalışıyordum, ardından hile yaptım ..
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));
Sonuç şöyle olacaktır:
["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"]
Bir süredir @Mohammed Safeer çözümünü kullanıyorum ve birkaç iyileştirme yaptım. Denetleyicilerinizde çalışırken biçimlendirilmiş tarihler kullanmak kötü bir uygulamadır. moment().format()
görünümlerde yalnızca görüntüleme amacıyla kullanılmalıdır. Ayrıca moment().clone()
, girdi parametrelerinden ayrılmayı sağladığını, yani girdi tarihlerinin değiştirilmediğini unutmayın. Tarihlerle çalışırken moment.js kullanmanızı şiddetle tavsiye ederim.
Kullanım:
startDate
, endDate
parametrelerinterval
parametresi isteğe bağlıdır ve varsayılan olarak "günler" dir. .add()
Yöntem (moment.js) tarafından desteklenen aralıkları kullanın . Daha fazla ayrıntı buradatotal
parametresi, dakika cinsinden aralıkları belirtirken kullanışlıdır. Varsayılan olarak 1'dir.Çağırmak:
var startDate = moment(),
endDate = moment().add(1, 'days');
getDatesRangeArray(startDate, endDate, 'minutes', 30);
İşlev:
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;
};
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
önce strDate
while döngüsünün içine girmemelisin!
Bu işlevi kullanıyorum
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;
}
Tarihleri arasını hesaplamak için basit while döngüsü kullanıyorum
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);
}
MomentJS kullanarak kolayca yapabilirsiniz
Bağımlılıklarınıza an ekleyin
npm i moment
Sonra bunu dosyanıza aktarın
var moment = require("moment");
Ardından, iki tarih arasındaki tüm tarihlerin listesini almak için aşağıdaki kodu kullanın
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);
d3js birçok kullanışlı işlev sağlar ve kolay tarih manipülasyonları için d3.time içerir
Özel isteğiniz için:
UTC
var range = d3.utcDay.range(new Date(), d3.utcDay.offset(new Date(), 7));
veya yerel saat
var range = d3.timeDay.range(new Date(), d3.timeDay.offset(new Date(), 7));
aralık, her gün için ilk olası değere denk gelen bir tarih nesneleri dizisi olacaktır
farklı aralıklarda aynı sonuçlar için gün saatini, saati, ayı vb. değiştirebilirsiniz.
Başka bir işlev oluşturmak istememeniz durumunda herhangi bir kitaplık gerektirmeyen bir satır burada. Sadece startDate (iki yerde) ve endDate'i (js date nesneleridir) değişkenleriniz veya tarih değerlerinizle değiştirin. Elbette tercih ederseniz bir fonksiyona da sarabilirsiniz
Array(Math.floor((endDate - startDate) / 86400000) + 1).fill().map((_, idx) => (new Date(startDate.getTime() + idx * 86400000)))
Not: Bunun istenen çözümden biraz farklı olduğunun farkındayım, ancak birçok kişinin onu faydalı bulacağını düşünüyorum.
İki tarih arasındaki her "x" aralığını (günler, aylar, yıllar vb.) Bulmak istiyorsanız , moment.js ve moment-aralık genişletme paketleri bu işlevi etkinleştirir.
Örneğin, iki tarih arasındaki her 30. günü bulmak için :
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'))
});
Yıl dizisi oluşturun:
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())
Ay için bir dizi oluşturun:
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())
Günler için bir dizi oluşturun:
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())
Yukarıdaki cevapları kullanırken sorun yaşadım. Yerel gün ışığından yararlanma saatinden (DST) kaynaklanan saat dilimi kayması nedeniyle tarih aralıklarında tek günler eksikti. Bu sorunu gideren UTC tarihlerini kullanan bir sürüm uyguladım:
function dateRange(startDate, endDate, steps = 1) {
const dateArray = [];
let currentDate = new Date(startDate);
while (currentDate <= new Date(endDate)) {
dateArray.push(new Date(currentDate));
// Use UTC date to prevent problems with time zones and DST
currentDate.setUTCDate(currentDate.getUTCDate() + steps);
}
return dateArray;
}
const dates = dateRange('2020-09-27', '2020-10-28');
console.log(dates);
Not : Belirli bir saat diliminin mi yoksa DST'nin mi uygulanıp uygulanmayacağı tamamen yerel ayarlarınıza bağlıdır . Bunu geçersiz kılmak genellikle iyi bir fikir değildir. UTC tarihlerini kullanmak çoğu zaman ilgili sorunları azaltır.
Bonus : Zaman damgası oluşturmak istediğiniz zaman aralığını isteğe bağlı steps
parametre ile ayarlayabilirsiniz . İsterseniz haftalık timetamps ayarlamak steps
için 7
.
Bu birine yardımcı olabilir,
Bundan satır çıktısını alabilir ve row_date nesnesini istediğiniz gibi biçimlendirebilirsiniz.
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
İşte Moment tarihlerini veya dizelerini veya bir karışımı giriş olarak kabul edecek ve An tarihleri olarak bir tarih dizisi oluşturacak hazır bir yöntem. Moment tarihlerini çıktı olarak istemiyorsanız, map()
yöntemin döndürdüğü şeyi değiştirin .
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'ın çözümü, ancak daha sonra çalışma tarihleri seçeneği dahil
/**
* 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;
}
İşlev:
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;
};
Kullanım:
var dates = getDatesRange(new Date(2019,01,01), new Date(2019,01,25));
dates.forEach(function(date) {
console.log(date);
});
Umarım sana yardımcı olur
Ben böyle yapmaktan hoşlanıyorum
// hours * minutes * seconds * milliseconds
const DAY_IN_MS = 24 * 60 * 60 * 1000
/**
* Get range of dates
* @param {Date} startDate
* @param {Number} numOfDays
* @returns {array}
*/
const dateRange = (startDate, numOfDays) => {
const startDateMs = startDate.getTime()
// get array of days and map it to Date object
return [...Array(numOfDays).keys()].map(i => new Date(startDateMs + i * DAY_IN_MS))
}