Usuário com melhor resposta
Passar List<T> como parâmetro para um Form - C# Windows Form

Pergunta
-
Olá pessoa do fórum, estou com uma grande dúvida a cerca de passar uma lista genérica como parâmetro para um outro form do meu projeto. A principio eu passei essa List<T> como valor para o formulário porém está acontecendo algo muito estranho, ao realizar qualquer alteração nesta lista no segundo formulário a mesma é alterada no formulário principal, como se ambas tivesse com o mesmo endereço de memória, e esse comportamento ocorre apenas com as List<T>. Segue abaixo um pequeno exemplo para ficar mais claro a minha dúvida.
Formulário Secundário
public List<Pessoa> listaPessoaSecundaria; public Form2(List<Pessoa> listaPessoa) { InitializeComponent(); listaPessoaSecundaria = listaPessoa; }
Formulário Primário
List<Pessoa> listaPessoaPrincipal; private void Form1_Load(object sender, EventArgs e) { listaPessoaPrincipal = ObterListaPessoa(); dataGridView1.DataSource = listaPessoaPrincipal; } private void button1_Click(object sender, EventArgs e) { Form2 secundario = new Form2(listaPessoaPrincipal); if (secundario.ShowDialog() == DialogResult.OK) { listaPessoaPrincipal = secundario.listaPessoaSecundaria; dataGridView1.DataSource = null; dataGridView1.DataSource = listaPessoaPrincipal; } else { dataGridView1.DataSource = null; dataGridView1.DataSource = listaPessoaPrincipal; } }
Se alguém puder me ajudar serei muito grato.
Respostas
-
Não, veja uma explicação aqui https://msdn.microsoft.com/pt-br/library/14akc2c7.aspx?f=255&MSPPError=-2147217396 . Particularmente eu uso REF em tipos primários (int, double, float...) para serem passados como referencia.
int x = 1; Change(ref x); Debug.Assert(x == 5); // true WillNotChange(x); Debug.Assert(x == 5); // false - x não está com valor 10 void Change(ref int x) { x = 5; } void WillNotChange(int x) { x = 10; }
Objetos no C# são passados como referência (tirando string que é um caso a parte, http://stackoverflow.com/questions/1096449/c-sharp-string-reference-type).
Att. Andre de Mattos Ferraz - www.iamferraz.com.br - http://mbsy.co/ldecrespigny/19022985
- Editado André de Mattos Ferraz quinta-feira, 3 de março de 2016 13:50
- Marcado como Resposta Marcos SJ quinta-feira, 3 de março de 2016 14:09
-
Tem, vc clona ela e passa :D
veja aqui http://stackoverflow.com/questions/222598/how-do-i-clone-a-generic-list-in-c
var newList = oldList.ToList();
Att. Andre de Mattos Ferraz - www.iamferraz.com.br - http://mbsy.co/ldecrespigny/19022985
- Editado André de Mattos Ferraz quinta-feira, 3 de março de 2016 14:10
- Marcado como Resposta J.AndersonSantos quinta-feira, 3 de março de 2016 14:32
-
Anderson bom dia!
Tem um tópico bem explicativo no StackOverFlow que deve te ajudar:
Passagem por valor ou por referência
Resumindo, o que é dito é que quando você passar a referencia do objeto é como se você tivesse dois objetos iguais, apontando pro mesmo local na memória sim. Enquanto quando você passar por valor, você faz uma cópia do valor e armazena no objeto novo.
Olha um exemplo bobo que fiz aqui:
class Program { static void Main(string[] args) { Animal animal1 = new Animal(); animal1.Tipo = "Mamífero"; animal1.Nome = "Totó"; Animal animal2 = new Animal(); animal2.Tipo = "Peixe"; animal2.Nome = "Linguado"; animal1.Nome = animal2.Nome; Console.WriteLine(animal1.Nome); //Imprime Linguado Console.WriteLine(animal1 == animal2); //Imprime False Console.ReadKey(); animal2.Nome = "Qualquer Coisa"; Console.WriteLine(animal1.Nome); //Imprime Linguado, pois ele copiou este valor do objeto animal2 e mesmo com a alteração do objeto animal2, não houve alteração no objeto animal1 Console.WriteLine(animal1 == animal2); //Imprime false Console.ReadKey(); animal1 = animal2; animal2.Nome = "Qualquer Coisa de novo"; Console.WriteLine(animal1.Nome); //Imprime Qualquer Coisa de novo, pois agora animal1 é apontado para o mesmo local de animal2 Console.WriteLine(animal1 == animal2); //Imprime True Console.ReadKey(); } }
Veja se te ajuda.
Abraços!
- Marcado como Resposta Levi DomingosModerator quinta-feira, 3 de março de 2016 16:18
Todas as Respostas
-
-
Obrigado pela resposta André, porém eu tenho uma dúvida para ser por referência não seria:
public Form2(ref List<Pessoa> listaPessoa) { InitializeComponent(); listaPessoaSecundaria = listaPessoa; }
Você informou na sua resposta que List<Pessoa> está sendo passada por referência, então qual seria a forma de passar uma cópia apenas. Para que listaPessoaPrincipal e listaPessoaSecundaria sejam diferente.
-
Não, veja uma explicação aqui https://msdn.microsoft.com/pt-br/library/14akc2c7.aspx?f=255&MSPPError=-2147217396 . Particularmente eu uso REF em tipos primários (int, double, float...) para serem passados como referencia.
int x = 1; Change(ref x); Debug.Assert(x == 5); // true WillNotChange(x); Debug.Assert(x == 5); // false - x não está com valor 10 void Change(ref int x) { x = 5; } void WillNotChange(int x) { x = 10; }
Objetos no C# são passados como referência (tirando string que é um caso a parte, http://stackoverflow.com/questions/1096449/c-sharp-string-reference-type).
Att. Andre de Mattos Ferraz - www.iamferraz.com.br - http://mbsy.co/ldecrespigny/19022985
- Editado André de Mattos Ferraz quinta-feira, 3 de março de 2016 13:50
- Marcado como Resposta Marcos SJ quinta-feira, 3 de março de 2016 14:09
-
-
Tem, vc clona ela e passa :D
veja aqui http://stackoverflow.com/questions/222598/how-do-i-clone-a-generic-list-in-c
var newList = oldList.ToList();
Att. Andre de Mattos Ferraz - www.iamferraz.com.br - http://mbsy.co/ldecrespigny/19022985
- Editado André de Mattos Ferraz quinta-feira, 3 de março de 2016 14:10
- Marcado como Resposta J.AndersonSantos quinta-feira, 3 de março de 2016 14:32
-
Anderson bom dia!
Tem um tópico bem explicativo no StackOverFlow que deve te ajudar:
Passagem por valor ou por referência
Resumindo, o que é dito é que quando você passar a referencia do objeto é como se você tivesse dois objetos iguais, apontando pro mesmo local na memória sim. Enquanto quando você passar por valor, você faz uma cópia do valor e armazena no objeto novo.
Olha um exemplo bobo que fiz aqui:
class Program { static void Main(string[] args) { Animal animal1 = new Animal(); animal1.Tipo = "Mamífero"; animal1.Nome = "Totó"; Animal animal2 = new Animal(); animal2.Tipo = "Peixe"; animal2.Nome = "Linguado"; animal1.Nome = animal2.Nome; Console.WriteLine(animal1.Nome); //Imprime Linguado Console.WriteLine(animal1 == animal2); //Imprime False Console.ReadKey(); animal2.Nome = "Qualquer Coisa"; Console.WriteLine(animal1.Nome); //Imprime Linguado, pois ele copiou este valor do objeto animal2 e mesmo com a alteração do objeto animal2, não houve alteração no objeto animal1 Console.WriteLine(animal1 == animal2); //Imprime false Console.ReadKey(); animal1 = animal2; animal2.Nome = "Qualquer Coisa de novo"; Console.WriteLine(animal1.Nome); //Imprime Qualquer Coisa de novo, pois agora animal1 é apontado para o mesmo local de animal2 Console.WriteLine(animal1 == animal2); //Imprime True Console.ReadKey(); } }
Veja se te ajuda.
Abraços!
- Marcado como Resposta Levi DomingosModerator quinta-feira, 3 de março de 2016 16:18
-