2013-07-05 13 views
6

Mam ten naprawdę dziwny problem i jestem pewien, że brakuje tu czegoś oczywistego. Mam te dwie linie:Obiekt sesji zmienia się, gdy obiekt jest aktualizowany w C#

HttpContext.Current.Session[listModelType + "ListModel"] = listModel; 
listModel.ProductRows = new Collection<ProductRow>(listModel.ProductRows.Where(r => r.ParentRowId == 0).ToList()); 

Po drugiej linii jest wykonywany mojego obiektu sesja jest zaktualizowane, a także (zgodnie z „Watch” w Visual Studio)

Co ja tu brakuje?

Próbowałem

int i = 0; 
HttpContext.Current.Session["i"] = i; 
i++; 

i HttpContext.Current.Session [ "i"] pozostaje 0.

Odpowiedz

11

Zobacz value types and reference types.

int jest typem wartości, więc będzie przechowywany "tak jak jest" w momencie przypisania; twój listModel jest typem referencyjnym, więc przechowujesz odniesienie do obiektu w twojej sesji, a nie wartość obiektu.

Musisz utworzyć nową instancję z listModel, jeśli chcesz, aby ta w twojej sesji była nietknięta.

+0

Dzięki CodeCaster - dasz radę. Pomyślałem, że zawsze była to wartość, która była przechowywana. – CJe

+0

Twoje prawo z tym, co myślałeś, wartości są przechowywane w sesjach – rajeemcariazo

4

W pierwszym przykładzie przechowujesz odniesienie do obiektu (Lista lokalizacji pamięci). Więc jeśli aktualizacja list zostanie zaktualizowana, odzwierciedli się w sesji. To jest typ odniesienia.

W drugim przykładzie używasz typ wartości:

int i = 0; 
HttpContext.Current.Session["i"] = i; 
i++; 

zadeklarować i i ustawić ją na 0 (typ wartości)

przechowywać wartość 0 w sesji. (Nie miejsce pamięci i)

można zwiększyć i ale sesja nadal ma wartość 0

1

w pierwszym przykładzie zmienna sesja wskazując na reference więc jest ona aktualizowana, ponieważ dwie referencje są skierowane do ta sama wartość.

Druga zmienna sesji wskazuje na typ primitive (value), więc mają oddzielne kopie wartości.

0

Prawidłowy sposób powinno być:

int i = 0; 
    i++; 
    HttpContext.Current.Session["i"] = i; 

HttpContext.Current.Session [ "i"] pozostaje 1.

1

W pierwszym przykładzie zmienna sesja jest skierowana do odniesienia tak jest aktualizowany, ponieważ dwa odwołania wskazują na tę samą wartość.

więc przed przypisaniem do sesji przekonwertować go do Json a następnie przypisać

HttpContext.Current.Session[listModelType + "ListModel"] = JsonConvert.SerializeObject(listModel); 

Uwaga: JsonConvert jest z kosmosu nazwa Newtonsoft.Przestrzeń nazw Json w C#

W drugiej linii, jeśli wartość zmienia się w obiekcie listModel, który nie odzwierciedla sesji. ale gdy chcesz retreive wartość z sesji należy przekonwertować do obiektu formularza JSON

if (HttpContext.Current.Session[listModelType + "ListModel"] != null) 
{ 

    listModel = JsonConvert.DeserializeObject<*CLASS name of lsitmodel*>((string)HttpContext.Current.Session[listModelType + "ListModel"]); 

} 
0

W pierwszym przykładzie zmienna sesja jest skierowana do odniesienia tak jest ona aktualizowana, ponieważ dwie referencje są skierowane do tego samego wartość.

więc przed przypisaniem do sesji przekonwertować go do Json a następnie przypisać

HttpContext.Current.Session[listModelType + "ListModel"] = JsonConvert.SerializeObject(listModel); 

Uwaga: JsonConvert wynosi od nazw Newtonsoft.Json przestrzeni nazw w języku C#

W drugiej linii jeżeli wartość zmienia się w listModel obiekt, który nie odzwierciedla sesji. ale gdy chcesz odzyskać wartość z sesji, powinieneś przekonwertować do postaci obiektu Json

if (HttpContext.Current.Session[listModelType + "ListModel"] != null) { 

     listModel = JsonConvert.DeserializeObject<*CLASS name of lsitmodel*>((string)HttpContext.Current.Session[listModelType + "ListModel"]); 

    } 
Powiązane problemy