@ ফাইরির খুব সহায়ক জবাব ছাড়াও এটি উল্লিখিত বাগের জন্য একটি Okayish workaround (এটির একটি) ), যে DatePeriod এক ঘন্টার substracts যখন গ্রীষ্মের লিখে, কিন্তু গ্রীষ্মের যাব (এবং এইভাবে ইউরোপ / বার্লিনের মার্চ তার রয়েছে এক ঘন্টার যোগ না সঠিক 743 ঘন্টা তবে অক্টোবরে 745 ঘন্টার পরিবর্তে 744 রয়েছে):
উভয় দিকে ডিএসটি-ট্রানজিশন বিবেচনা করে এক মাসের ঘন্টা (বা কোনও টাইমস্প্যান) গণনা করা হচ্ছে
function getMonthHours(string $year, string $month, \DateTimeZone $timezone): int
{
// or whatever start and end \DateTimeInterface objects you like
$start = new \DateTimeImmutable($year . '-' . $month . '-01 00:00:00', $timezone);
$end = new \DateTimeImmutable((new \DateTimeImmutable($year . '-' . $month . '-01 23:59:59', $timezone))->format('Y-m-t H:i:s'), $timezone);
// count the hours just utilizing \DatePeriod, \DateInterval and iterator_count, hell yeah!
$hours = iterator_count(new \DatePeriod($start, new \DateInterval('PT1H'), $end));
// find transitions and check, if there is one that leads to a positive offset
// that isn't added by \DatePeriod
// this is the workaround for https://bugs.php.net/bug.php?id=75685
$transitions = $timezone->getTransitions((int)$start->format('U'), (int)$end->format('U'));
if (2 === count($transitions) && $transitions[0]['offset'] - $transitions[1]['offset'] > 0) {
$hours += (round(($transitions[0]['offset'] - $transitions[1]['offset'])/3600));
}
return $hours;
}
$myTimezoneWithDST = new \DateTimeZone('Europe/Berlin');
var_dump(getMonthHours('2020', '01', $myTimezoneWithDST)); // 744
var_dump(getMonthHours('2020', '03', $myTimezoneWithDST)); // 743
var_dump(getMonthHours('2020', '10', $myTimezoneWithDST)); // 745, finally!
$myTimezoneWithoutDST = new \DateTimeZone('UTC');
var_dump(getMonthHours('2020', '01', $myTimezoneWithoutDST)); // 744
var_dump(getMonthHours('2020', '03', $myTimezoneWithoutDST)); // 744
var_dump(getMonthHours('2020', '10', $myTimezoneWithoutDST)); // 744
পিএস যদি আপনি একটি (দীর্ঘতর) টাইমস্প্যান পরীক্ষা করেন যা এই দুটি স্থানান্তরের চেয়ে বেশি দিকে পরিচালিত করে, মজাদার পার্শ্ব প্রতিক্রিয়াগুলির সম্ভাবনা হ্রাস করতে আমার কর্মপরিকল্পনা গণনার সময়গুলিকে স্পর্শ করবে না। এই ধরনের ক্ষেত্রে, আরও জটিল সমাধান অবশ্যই প্রয়োগ করা উচিত। সমস্ত পাওয়া ট্রানজিশনগুলিতে পুনরাবৃত্তি করতে পারে এবং শেষের সাথে বর্তমানের তুলনা করতে পারে এবং এটি ডিএসটি সত্য-> মিথ্যা দিয়ে কিনা তা পরীক্ষা করতে পারে।
strftime()এবং পার্থক্যটিকে 3600 দ্বারা বিভক্ত করুন, তবে কি এটি সর্বদা কার্যকর হবে? অভিশাপ, দিবালোক সঞ্চয় সময়!