Cannot implicitly convert type 'customtype' to 'othercustomtype'

前端 未结 5 847
鱼传尺愫
鱼传尺愫 2020-12-06 17:25

I am new to C#. I have a Persons class and a User class which inherits from the Persons class. I my console I input a users in an array. Then I can add a note to a user that

相关标签:
5条回答
  • 2020-12-06 18:05

    Anyway, I recommend to use LINQ extension method for your first method:

    using System.Collections.Generic;
    using System.Linq;
    
    public static Persons FindPerson(IEnumerable<Person> persons, int id)
    {
        return persons.FirstOrDefault(p => p.ID == id);
    }
    

    Looks much better, right?

    0 讨论(0)
  • 2020-12-06 18:07

    You should rewrite the return snippet like so:

    User user = Persons.FindPerson(users, id) as User;
    if (user != null) return user;
    

    The problem you were having was to do with you trying to return a base class from a method that should return a more derived class. The compiler cannot automatically downcast(Persons->User), but it can upcast (User->Persons)

    0 讨论(0)
  • 2020-12-06 18:11

    Because a Person is not nessecarily a User, the compiler is not able to implicitly convert a Person to a User. In your particular case, since you know you have a list of Users, you can explicitly tell it, "I know this Person is actually a User" with the following:

    if (person != null)
       return (User) person;
    

    The cast ((User)) will throw an exception at runtime if the instance is not actually a User, but since you've started with a collection of Users to begin with, you don't need to worry.

    0 讨论(0)
  • 2020-12-06 18:11

    Since User inherits from Person, you cannot implicitly convert any random Person to a User (though you can implicitly convert a User to a Person).

    Since you pass a User[] to FindPerson(users, id), you can be sure the returned person is indeed a User, so you can cast it like this:

    return (User)person;
    

    Edit: You might consider using generics on FindPerson to avoid the cast altogether.

    public static T FindPerson<T>(IEnumerable<T> persons, int noteid)
        where T : Person
    {
        foreach (T person in persons)
        {
            if (person.ID == noteid)
            {
                return person;
            }
        }
    
        return null;
    }
    
    public static User SelectUser(User[] users)
    {
        while (true)
        {
            Console.Write("Please enter the User id: ");
            string input = Console.ReadLine();
            int id;
            if (int.TryParse(input, out id))
            {
                User person = Persons.FindPerson(users, id);
                if (person != null)
                {
                    return person;
                }            
            }
    
            Console.WriteLine("The User does not exist. Please try again.");                
        }
    }
    
    0 讨论(0)
  • 2020-12-06 18:19

    You need to implement explicit or implicit operator:

    class ClassA
    {
        public string Property1 { get; set; }
    
        public static explicit operator ClassB(ClassA classA)
        {
            return new ClassB() { Property2 = classA.Property1 };
        }
    }
    
    class ClassB
    {
        public string Property2 { get; set; }
    }
    
    var a = new ClassA() {Property1 = "test"};
    ClassB b = (ClassB)a;
    Console.WriteLine(b.Property2); // output is "test"
    
    0 讨论(0)
提交回复
热议问题