如何在 C# 中使用单独的类来验证信用卡号码

发布于 2024-09-01 12:37:43 字数 1749 浏览 3 评论 0原文

我已经设置了一个类来验证信用卡号。信用卡类型和号码是在单独类别的表格上选择的。我试图弄清楚如何将在其他类(frmPayment)中选择的信用卡类型和号码添加到我的信用卡类算法中:

public enum CardType
{
    MasterCard, Visa, AmericanExpress
}

public sealed class CardValidator
{
    public static string SelectedCardType { get; private set; }
    public static string CardNumber { get; private set; }

    private CardValidator(string selectedCardType, string cardNumber) 
    {
        SelectedCardType = selectedCardType;
        CardNumber = cardNumber;
    }

    public static bool Validate(CardType cardType, string cardNumber)
{
   byte[] number = new byte[16];


  int length = 0;
  for (int i = 0; i < cardNumber.Length; i++)
  {
      if (char.IsDigit(cardNumber, i))
      {
          if (length == 16) return false;
          number[length++] = byte.Parse(cardNumber[i]); //not working.  find different way to parse
      }
  }

  switch(cardType)
  {
     case CardType.MasterCard:
        if(length != 16)
           return false;
        if(number[0] != 5 || number[1] == 0 || number[1] > 5)
           return false;
        break;

     case CardType.Visa:
        if(length != 16 & length != 13)
           return false;
        if(number[0] != 4)
           return false;
        break;

     case CardType.AmericanExpress:
        if(length != 15)
           return false;
        if(number[0] != 3 || (number[1] != 4 & number[1] != 7))
           return false;
        break;

  }

  // Use Luhn Algorithm to validate
  int sum = 0;
  for(int i = length - 1; i >= 0; i--)
  {
     if(i % 2 == length % 2)
     {
        int n = number[i] * 2;
        sum += (n / 10) + (n % 10);
     }
     else
        sum += number[i];
  }
  return (sum % 10 == 0);

} }

I have set up a class to validate credit card numbers. The credit card type and number are selected on a form in a separate class. I'm trying to figure out how to get the credit card type and number that are selected in the other class (frmPayment) in to my credit card class algorithm:

public enum CardType
{
    MasterCard, Visa, AmericanExpress
}

public sealed class CardValidator
{
    public static string SelectedCardType { get; private set; }
    public static string CardNumber { get; private set; }

    private CardValidator(string selectedCardType, string cardNumber) 
    {
        SelectedCardType = selectedCardType;
        CardNumber = cardNumber;
    }

    public static bool Validate(CardType cardType, string cardNumber)
{
   byte[] number = new byte[16];


  int length = 0;
  for (int i = 0; i < cardNumber.Length; i++)
  {
      if (char.IsDigit(cardNumber, i))
      {
          if (length == 16) return false;
          number[length++] = byte.Parse(cardNumber[i]); //not working.  find different way to parse
      }
  }

  switch(cardType)
  {
     case CardType.MasterCard:
        if(length != 16)
           return false;
        if(number[0] != 5 || number[1] == 0 || number[1] > 5)
           return false;
        break;

     case CardType.Visa:
        if(length != 16 & length != 13)
           return false;
        if(number[0] != 4)
           return false;
        break;

     case CardType.AmericanExpress:
        if(length != 15)
           return false;
        if(number[0] != 3 || (number[1] != 4 & number[1] != 7))
           return false;
        break;

  }

  // Use Luhn Algorithm to validate
  int sum = 0;
  for(int i = length - 1; i >= 0; i--)
  {
     if(i % 2 == length % 2)
     {
        int n = number[i] * 2;
        sum += (n / 10) + (n % 10);
     }
     else
        sum += number[i];
  }
  return (sum % 10 == 0);

}
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

饮湿 2024-09-08 12:37:43

您错过了获得更好的 OOP 和更清晰的代码的绝佳机会。

class CreditCard
{
   public CreditCard(string number, string expiration, string cvv2) {...}

   public virtual bool IsValid()
   {
       /* put common validation logic here */
   }

   /* factory for actual cards */
   public static CreditCard GetCardByType (CardType card, string number, string expiration, string cvv2)
   {
        switch (card)
        {
             case  CardType.Visa:
                  return new VisaCreditCard(...);

             ...
        }
   }
}

class VisaCreditCard : CreditCard
{
   public VisaCreditCard (string number, string expiration, string cvv2 )
      : base (number, expiration, cvv2)
   {...}

   public override bool IsValid()
   {
       /* check Visa rules... */
       bool isValid = ...

       return isValid & base.IsValid();
   }
}

You're missing a great opportunity for better OOP and cleaner code.

class CreditCard
{
   public CreditCard(string number, string expiration, string cvv2) {...}

   public virtual bool IsValid()
   {
       /* put common validation logic here */
   }

   /* factory for actual cards */
   public static CreditCard GetCardByType (CardType card, string number, string expiration, string cvv2)
   {
        switch (card)
        {
             case  CardType.Visa:
                  return new VisaCreditCard(...);

             ...
        }
   }
}

class VisaCreditCard : CreditCard
{
   public VisaCreditCard (string number, string expiration, string cvv2 )
      : base (number, expiration, cvv2)
   {...}

   public override bool IsValid()
   {
       /* check Visa rules... */
       bool isValid = ...

       return isValid & base.IsValid();
   }
}
執念 2024-09-08 12:37:43

对于初学者来说,我会使用正则表达式进行简单的验证(所有数字,特定长度)。

但就你的问题而言,我不确定我是否理解问题所在。从您在这里发布的内容来看,您似乎应该删除构造函数并将整个内容设为静态类。

public enum CardType
{
    MasterCard,
    Visa,
    AmericanExpress,
}

public static class CardValidator
{
    public static bool Validate(CardType cardType, string cardNumber)
    {
        string strippedCardNumber = Regex.Replace(cardNumber, @"\D", String.Empty);


        ICardValidator validator = SelectCardValidator(cardType);

        return validator.Validate(strippedCardNumber);
    }

    private static ICardValidator SelectCardValidator(CardType cardType)
    {
        switch (cardType)
        {
            case CardType.MasterCard:
                return new MasterCardValidator();
            case CardType.Visa:
                return new VisaValidator();
            case CardType.AmericanExpress:
                return new AmericanExpressValidator();
            default:
                return new UnknownCardTypeValidator();
        }
    }

    private interface ICardValidator
    {
        bool Validate(string cardNumber);
    }

    private class UnknownCardTypeValidator : ICardValidator
    {
        #region ICardValidator Members

        public bool Validate(string cardNumber)
        {
            return false;
        }

        #endregion
    }

    private abstract class LuhnAlgorithmValidator : ICardValidator
    {

        #region ICardValidator Members

        public virtual bool Validate(string cardNumber)
        {
            // Implement Luhn Algorithm here

            return false;
        }

        #endregion
    }

    private class MasterCardValidator : LuhnAlgorithmValidator
    {
        public override bool Validate(string cardNumber)
        {
            bool isValid = false; // replace with MasterCard validation
            return isValid && base.Validate(cardNumber);
        }
    }

    private class VisaValidator : LuhnAlgorithmValidator
    {
        public override bool Validate(string cardNumber)
        {
            bool isValid = false; // replace with Visa validation
            return isValid && base.Validate(cardNumber);
        }
    }

    private class AmericanExpressValidator : LuhnAlgorithmValidator
    {
        public override bool Validate(string cardNumber)
        {
            bool isValid = false; // replace with AmEx validation
            return isValid && base.Validate(cardNumber);
        }
    }
}

For starters, I'd use Regex to do the simple validation (all digits, specific length.)

But to the point of your question, I'm not sure I understand what the issue is. From what you've posted here, it looks like you should probably drop the constructor and make the whole thing a static class.

public enum CardType
{
    MasterCard,
    Visa,
    AmericanExpress,
}

public static class CardValidator
{
    public static bool Validate(CardType cardType, string cardNumber)
    {
        string strippedCardNumber = Regex.Replace(cardNumber, @"\D", String.Empty);


        ICardValidator validator = SelectCardValidator(cardType);

        return validator.Validate(strippedCardNumber);
    }

    private static ICardValidator SelectCardValidator(CardType cardType)
    {
        switch (cardType)
        {
            case CardType.MasterCard:
                return new MasterCardValidator();
            case CardType.Visa:
                return new VisaValidator();
            case CardType.AmericanExpress:
                return new AmericanExpressValidator();
            default:
                return new UnknownCardTypeValidator();
        }
    }

    private interface ICardValidator
    {
        bool Validate(string cardNumber);
    }

    private class UnknownCardTypeValidator : ICardValidator
    {
        #region ICardValidator Members

        public bool Validate(string cardNumber)
        {
            return false;
        }

        #endregion
    }

    private abstract class LuhnAlgorithmValidator : ICardValidator
    {

        #region ICardValidator Members

        public virtual bool Validate(string cardNumber)
        {
            // Implement Luhn Algorithm here

            return false;
        }

        #endregion
    }

    private class MasterCardValidator : LuhnAlgorithmValidator
    {
        public override bool Validate(string cardNumber)
        {
            bool isValid = false; // replace with MasterCard validation
            return isValid && base.Validate(cardNumber);
        }
    }

    private class VisaValidator : LuhnAlgorithmValidator
    {
        public override bool Validate(string cardNumber)
        {
            bool isValid = false; // replace with Visa validation
            return isValid && base.Validate(cardNumber);
        }
    }

    private class AmericanExpressValidator : LuhnAlgorithmValidator
    {
        public override bool Validate(string cardNumber)
        {
            bool isValid = false; // replace with AmEx validation
            return isValid && base.Validate(cardNumber);
        }
    }
}
少女的英雄梦 2024-09-08 12:37:43

frmPayments btnValidate_click (或类似)事件处理程序中,只需调用 CardValidator.Validate 方法。

但是,CardValidator 构造函数具有参数,即使它是私有的,并且从未被调用?为什么要向类添加属性?

编辑:错过了示例代码的一些部分。

In frmPayments btnValidate_click (or similar) event handler, just call CardValidator.Validate method.

However, the CardValidator constructor has parameters even though it's private, and never called? And why have you added properties to the class?

Edit: missed some bits of your sample code.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文