11
votes

Comment tester si une date d'heure est comprise entre 2 jours de semaine (Dayfweek)

en C #, donné un ensemble arbitraire de points de fin de journée (comme, Dayofweek.frifeek.friday et dayofweek.sunday) Comment un test) si une date arbitraire tombe entre ces deux jours, inclus?

Exemple: xxx

merci!


2 commentaires

Assumez-vous que la première journée reçue avant la deuxième journée? Par exemple, vous attendez-vous à votre algorithme de toujours répondre avec true si les jours étaient lundi et dimanche ?


Qu'il soit intentionnel ou involontaire, y compris dimanche comme l'un des arguments était un bon test, au moins dans la plupart des pays anglophones, car cela vous oblige à vous assurer que vous gérez la semaine enveloppante puisque le dimanche est 0.


6 Réponses :


0
votes

La réponse de Thomas Levesque est bonne ici. N'oubliez pas que dayofweek.sunday est 0 et pas 6 à l'intérieur de cette enum.

C'est problématique pour moi, car en Norvège lundi est le premier jour de la semaine et non dimanche.

Dans ce cas, vous devriez envisager de vérifier si l'ENum est égal à DayOfweek.sunday , et s'il doit ajouter 7 à la valeur avant de faire la comparaison pour vous assurer que le dimanche est considéré dans le manière correcte.

Si vous êtes dimanche comme premier jour de la semaine où vous vivez, ce n'est pas un problème de toute façon;)


4 commentaires

Non, ce n'est pas bon! L'algorithme @thomas n'apparaîtra jamais à vrai dans l'affaire présentée par l'OP.


Oui, c'est pourquoi j'ai dit que vous devez modifier dayofweek.sunday avant la comparaison, car il sera vrai pour les cas qui souhaitent. En outre, certains pays comptent dimanche comme le premier jour de la semaine, donc dans cette affaire, oui, mardi est entre dimanche et mercredi (pensez-y) ...;) ...;)


Le problème n'est pas de savoir si dimanche est le premier jour de la semaine ou non, le problème est que si vous choisissez un deuxième jour qui se produit plus tôt dans la semaine que le premier jour. , vous ne recevrez jamais de résultat positif . Pour donner un autre exemple, en utilisant dayofweek Enum math, mardi (2) sera jamais entre lundi (1) et dimanche (0)


Si vous faites la conversion appropriée d'abord, le dimanche ne sera pas 0, ce sera 7, il sera donc de vérifier si le mardi 2) est entre le lundi (1) et le dimanche (7).



7
votes

Chaque date tombe entre deux jours de deux jours de la semaine forte> (pensez-y) ...

Vous auriez besoin d'obtenir les dates de terminaison pour la Dayfweek le plus proche de la date en question ( où la différence de jour


note: strong> La solution suivante suppose une semaine à samedi au samedi fort> em > p>

Compte tenu des méthodes d'extension suivantes: p>

10/27/2010 (Wednesday) falls within the closest occurrences of Monday (10/25/2010) and Wednesday (10/27/2010)
10/28/2010 (Thursday) does not fall within the closest occurrences of Monday (10/25/2010) and Wednesday (10/27/2010)
10/29/2010 (Friday) does not fall within the closest occurrences of Monday (11/1/2010) and Wednesday (10/27/2010)
10/30/2010 (Saturday) does not fall within the closest occurrences of Monday (11/1/2010) and Wednesday (10/27/2010)
10/31/2010 (Sunday) does not fall within the closest occurrences of Monday (11/1/2010) and Wednesday (11/3/2010)
11/1/2010 (Monday) falls within the closest occurrences of Monday (11/1/2010) and Wednesday (11/3/2010)
11/2/2010 (Tuesday) falls within the closest occurrences of Monday (11/1/2010) and Wednesday (11/3/2010)
11/3/2010 (Wednesday) falls within the closest occurrences of Monday (11/1/2010) and Wednesday (11/3/2010) 


7 commentaires

J'aimerais pouvoir vous donner un autre vote. Semble tout le monde (sauf Øyvind Bråthen) avait stupide pour le petit-déjeuner :)


@leppie, on dirait que j'ai effrayé tous les autres! @Op, je travaille sur une vraie solution pour vous ...


Toutes mes excuses - aujourd'hui, j'ai appris à ne pas publier de réponses sur Stackoverflow avec une gueule de gueule


@Brad: Jetez un coup d'œil à ma suggestion ci-dessous. Je crois que cela n'exige pas qu'une semaine soit samedi - dimanche, mais une paire d'yeux supplémentaires sur elle ne ferait pas mal :)


IMHO, vous surchargez le problème ici.


@R. Bemrose, vous êtes correct. J'ai testé votre solution et ça marche magnifiquement, mais la culture ignorante.


@Bemrose, annulant mon commentaire précédent à propos de votre code n'étant pas compte de la culture. C'est très élégant!



0
votes

Je pense que cela devrait fonctionner. Il devrait également fonctionner indépendamment de ce que vous considérez comme le premier jour de la semaine: xxx

éditer:

Si vous vous demandez, le si <0 et + = 7 est de contourner cette soustraire deux jours, n'est pas conscient de la culture. Le code pourrait probablement être fait un peu plus propre, mais vous avez le point que je pense.


4 commentaires

Basé sur les exemples de l'OP, ils veulent pouvoir passer dans un UpperLimit qui se produit "plus tôt" dans la semaine que le inférieur . Pouvez-vous gérer ce cas?


@Brad: Où dans le OP, dit-il que le UpperLimit devrait être capable de se produire "antérieur" que le inférieur ? Et même si c'est le cas, mon code traiterait facilement cela également, en ajoutant un peu plus de logique au lieu de jeter une exception. Mon donne le résultat souhaité pour tous les exemples donnés au moins.


L'OP utilise les jours vendredi et dimanche , respectivement. Votre code lancerait une erreur.


@Brad: Et qu'est-ce qui vous fait croire que dimanche est le premier jour de la semaine dans la culture de l'OP et non lundi ?



14
votes

Cette fonction va avoir besoin de deux branches distinctes selon que la différence entre la date de début et la date est négative ou positive / zéro.

Je pourrais être totalement hors base, mais je pense que cela fonctionne pour tous les cas: xxx pré>

Pour référence, vos données de test ont renvoyé ce qui suit lorsque je l'ai exécuté et ajouté console.writeline pour chaque résultat: P>

True
True
True
False


9 commentaires

J'ai testé cela avec mes mêmes données d'échantillon: cela fonctionne comme le fait le mien. Pouvez-vous le faire connaître la culture? Je vous laisserai tous garder mes méthodes d'extension gratuitement :)


@Brad: Je ne suis pas vraiment sûr de ce que je devrais faire pour que sa culture soit consciente dans ce cas ... Je viens de supposer que cela fonctionnerait dans d'autres cultures, bien que je ne l'ai pas testé.


@Bemrose, toutes les évaluations ne seraient-elles pas toutes les évaluations de savoir si somedayofweek est <= à un autredayofweek présumée sur l'ordre du Sun-Sat (0-6) Dayfweek Enum?


@Brad: MSDN implique que 0 est toujours dimanche dans cet énum .


@Bemrose, Ouais, l'énum est la même dans toutes les cultures. Je suppose que vous avez raison que ce n'est pas d'importance quel jour si le PremierDayOftheweek dans votre solution. Ne vous inquiétez pas, vous avez le seul uppot que je peux vous donner il y a longtemps! :)


@Brad: En fait, j'ai dû vérifier cela ... Au début, je n'ai pas arrêté et pensez que la dateTime pourrait avoir une culture différente de la culture actuelle. C'est le matin, je peux dire. ;)


+1 Je pense que c'est la solution la plus propre qui a été postée. Je conviens que la culture devrait être non pertinente pour la solution, tant que la Dayfweek Enum va toujours de 0 à 6 jours et des jours consécutifs sont à côté de l'autre. Ma solution est plus complexe car j'ai pensé que nous devions résoudre le problème intermédiaire de "trouver tous les jours de la semaine entre deux jours de la semaine". Peut-être que la solution à ce problème est utile dans une autre circonstance, mais ce n'est pas le moyen le plus simple de résoudre la question de l'OP.


En outre, votre solution passe également tous mes tests.


Wow, je ne m'attendais pas à ces nombreuses réponses, merci beaucoup à tous!



6
votes

@ point de Brad que chaque jour de la semaine tombe entre deux jours de la semaine est valable. Cependant, nous supposons que les deux jours de la semaine en question sont commandé em>.

C'est, quand nous disons, "est de 30 Octobre 2010 (un samedi) entre le vendredi et le dimanche?" Em>, nous sommes vraiment demandent, "est de 30 Octobre, 2010 soit une ?. vendredi, un samedi ou un dimanche " em> p>

Cette observation nous permet de décomposer le problème en deux composants et résoudre le problème complet facilement: p>

1) déterminer si un jour particulier de la semaine est l'un d'un ensemble particulier de jours de la semaine (ce qui est trivial). p>

2) déterminer l'ensemble des jours de la semaine que vous prenez d'un jour à l'autre . Autrement dit, nous voulons une fonction qui retourne « vendredi, samedi, dimanche » quand donné « vendredi » et « dimanche », et que les retours « lundi, mardi, mercredi, jeudi, vendredi » quand donné « lundi » et « vendredi ». Ceci est la partie la plus délicate du problème. P>

Pour résoudre le second problème, nous marchons essentiellement à partir du premier jour du deuxième jour, de retour tous les jours entre les deux. Pour ce faire correctement, nous devons tenir compte du fait que le deuxième jour peut être inférieur au premier jour (au sens de représentation dimanche = 0 étant inférieur à vendredi = 5). Donc, nous procédons à la « promenade » dans un espace entier et ajouter 7 au deuxième jour si elle est inférieure au premier jour. Nous convertissons à jours-of-the-semaine espace (ce qui est des entiers modulo 7) sur la "sortie". P>

Voici le code et une série de tests qui permettent de résoudre cela. La méthode "GetDaysBetweenInclusive" résout le problème # 2, et "IsDayOfWeekBetween", ajoute la solution à un problème # 1 et permet de résoudre le problème de l'OP. P>

Profitez. P>

using System;
using System.Collections.Generic;
using System.Linq;
using NUnit.Framework;

namespace DayOfWeekUtilities
{
    public static class DayOfWeekHelpers
    {
        /// <summary>
        /// returns all days of the week, inclusive, from day1 to day2
        /// </summary>
        public static IEnumerable<DayOfWeek> GetDaysBetweenInclusive(DayOfWeek day1,
                                                                     DayOfWeek day2)
        {
            var final = (int)day2;
            if(day2 < day1)
            {
                final += 7;
            }
            var curr = (int)day1;
            do
            {
                yield return (DayOfWeek) (curr%7);
                curr++;
            } while (curr <= final);
        }

        /// <summary>
        /// returns true if the provided date falls on a day of the 
        /// week between day1 and day2, inclusive
        /// </summary>
        public static bool IsDayOfWeekBetween(this DateTime date,
                                              DayOfWeek day1,
                                              DayOfWeek day2)
        {
            return GetDaysBetweenInclusive(day1, day2).Contains(date.DayOfWeek);
        }
    }

    [TestFixture]
    public class Tests
    {
        [Test]
        public void Test()
        {
            Assert.IsTrue(new DateTime(2010, 10, 22).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Sunday));
            Assert.IsTrue(new DateTime(2010, 10, 23).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Sunday));
            Assert.IsTrue(new DateTime(2010, 10, 24).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Sunday));
            Assert.IsFalse(new DateTime(2010, 10, 25).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Sunday));
            Assert.IsFalse(new DateTime(2010, 10, 26).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Sunday));
            Assert.IsFalse(new DateTime(2010, 10, 27).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Sunday));
            Assert.IsFalse(new DateTime(2010, 10, 28).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Sunday));
            Assert.IsTrue(new DateTime(2010, 10, 29).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Sunday));

            Assert.IsTrue(new DateTime(2010, 10, 22).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Friday));
            Assert.IsFalse(new DateTime(2010, 10, 23).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Friday));
            Assert.IsFalse(new DateTime(2010, 10, 24).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Friday));
            Assert.IsFalse(new DateTime(2010, 10, 25).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Friday));
            Assert.IsFalse(new DateTime(2010, 10, 26).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Friday));
            Assert.IsFalse(new DateTime(2010, 10, 27).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Friday));
            Assert.IsFalse(new DateTime(2010, 10, 28).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Friday));
            Assert.IsTrue(new DateTime(2010, 10, 29).IsDayOfWeekBetween(DayOfWeek.Friday, DayOfWeek.Friday));

            Assert.IsTrue(new DateTime(2010, 10, 22).IsDayOfWeekBetween(DayOfWeek.Monday, DayOfWeek.Friday));
            Assert.IsFalse(new DateTime(2010, 10, 23).IsDayOfWeekBetween(DayOfWeek.Monday, DayOfWeek.Friday));
            Assert.IsFalse(new DateTime(2010, 10, 24).IsDayOfWeekBetween(DayOfWeek.Monday, DayOfWeek.Friday));
            Assert.IsTrue(new DateTime(2010, 10, 25).IsDayOfWeekBetween(DayOfWeek.Monday, DayOfWeek.Friday));
            Assert.IsTrue(new DateTime(2010, 10, 26).IsDayOfWeekBetween(DayOfWeek.Monday, DayOfWeek.Friday));
            Assert.IsTrue(new DateTime(2010, 10, 27).IsDayOfWeekBetween(DayOfWeek.Monday, DayOfWeek.Friday));
            Assert.IsTrue(new DateTime(2010, 10, 28).IsDayOfWeekBetween(DayOfWeek.Monday, DayOfWeek.Friday));
            Assert.IsTrue(new DateTime(2010, 10, 29).IsDayOfWeekBetween(DayOfWeek.Monday, DayOfWeek.Friday));

            Assert.IsTrue(new DateTime(2010, 10, 22).IsDayOfWeekBetween(DayOfWeek.Thursday, DayOfWeek.Tuesday));
            Assert.IsTrue(new DateTime(2010, 10, 23).IsDayOfWeekBetween(DayOfWeek.Thursday, DayOfWeek.Tuesday));
            Assert.IsTrue(new DateTime(2010, 10, 24).IsDayOfWeekBetween(DayOfWeek.Thursday, DayOfWeek.Tuesday));
            Assert.IsTrue(new DateTime(2010, 10, 25).IsDayOfWeekBetween(DayOfWeek.Thursday, DayOfWeek.Tuesday));
            Assert.IsTrue(new DateTime(2010, 10, 26).IsDayOfWeekBetween(DayOfWeek.Thursday, DayOfWeek.Tuesday));
            Assert.IsFalse(new DateTime(2010, 10, 27).IsDayOfWeekBetween(DayOfWeek.Thursday, DayOfWeek.Tuesday));
            Assert.IsTrue(new DateTime(2010, 10, 28).IsDayOfWeekBetween(DayOfWeek.Thursday, DayOfWeek.Tuesday));
            Assert.IsTrue(new DateTime(2010, 10, 29).IsDayOfWeekBetween(DayOfWeek.Thursday, DayOfWeek.Tuesday));
        }
    }
}


1 commentaires

+1 Pour une solution qui ne résout pas seulement le problème complètement, mais le fait de manière très élégante. Ce n'est peut-être pas la solution la plus propre, mais c'est définitivement celui qui est le plus facile à comprendre. Belle façon d'analyser le problème Stuart :)



0
votes

Stuart Lauge dit: ... Effectuez la "promenade" dans un espace entier. Je comprends: xxx


0 commentaires