Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:

C# для чайников

.pdf
Скачиваний:
183
Добавлен:
27.03.2015
Размер:
15.52 Mб
Скачать

DisplayArray [ I D i s p l a y a b l e

[] d i s p l a y a b l e s )

{

 

 

 

i n t l e n g t h =

d i s p l a y a b l e s . L e n g t h ;

 

f o r ( i n t i n d e x = 0 ; i n d e x < l e n g t h ;

i n d e x + + )

{

 

 

 

I D i s p l a y a b l e

d i s p l a y a b l e

= d i s p l a y a b l e s [ i n d e x ] ;

C o n s o l e . W r i t e L i n e ( " { 0 } " ,

d i s p l a y a b l e . G e t S t r i n g ( ) ) ;

/ / S t u d e n t s - с о р т и р о в к а п о у с п е в а е м о с т и

// S t u d e n t - о п и с а н и е с т у д е н т а с и с п о л ь з о в а н и е м и м е н и и // у с п е в а е м о с т и

class S t u d e n t : I C o m p a r a b l e , I D i s p l a y a b l e

(

p r i v a t e

s t r i n g

p r i v a t e

d o u b l e

s N a m e ;

d G r a d e = 0 . 0 ;

/ / К о н с т р у к т о р - и н и ц и а л и з а ц и я н о в о г о о б ъ е к т а p u b l i c S t u d e n t ( s t r i n g s N a m e , d o u b l e d G r a d e )

t h i s . s N a m e = s N a m e ;

t h i s . d G r a d e = d G r a d e ;

/ / C r e a t e S t u d e n t L i s t - д л я п р о с т о т ы п р о с т о с о з д а е м

/ / ф и к с и р о в а н н ы й с п и с о к с т у д е н т о в

 

 

 

s t a t i c s t r i n g [ ]

s N a m e s =

 

 

 

 

 

{ " H o m e r " ,

" M a r g e " ,

" B a r t " ,

" L i s a " ,

" M a g g i e " } ;

s t a t i c d o u b l e t ]

d G r a d e s =

{ 0 , 8 5 ,

5 0 ,

1 0 0 ,

3 0 } ;

p u b l i c s t a t i c S t u d e n t [ ] C r e a t e S t u d e n t L i s t ( )

 

{

 

 

 

 

 

 

 

 

 

 

S t u d e n t [ ]

s A r r a y = n e w S t u d e n t [ s N a m e s . L e n g t h ] ;

for

( i n t

i

=

0;

i <

s N a m e s . L e n g t h ; i + + )

 

{

 

 

 

 

 

 

 

 

 

 

s A r r a y t i ]

= n e w S t u d e n t ( s N a m e s [ i ] ,

d G r a d e s [ i ] ) ;

}

 

 

 

 

 

 

 

 

 

 

r e t u r n

s A r r a y ;

 

 

 

 

 

 

/ / Методы

д о с т у п а

т о л ь к о

д л я ч т е н и я

 

 

public

s t r i n g

N a m e

 

 

 

 

 

get

{ r e t u r n

s N a m e ;

}

 

 

 

 

public

d o u b l e

G r a d e

 

 

 

 

 

get

{ r e t u r n

d G r a d e ;

}

 

 

 

 

// Р е а л и з а ц и я

//CompareTo

и н т е р ф е й с а I C o m p a r a b l e :

- с р а в н е н и е д в у х о б ъ е к т о в (в н а ш е м с л у ч а е —

ю 14. Интерфейсы и структуры

319

/ /

о б ъ е к т о в

т и

п а S t u d e n t ) и

в ы я с н е н и е т о г о , ч т о и з них

/ /

д о л ж е н и д т и

р а н ь ш е в о т с о р т и р о в а н н о м с п и с к е

p u b l i c i n t

C o m p a r e T o ( o b j e c t

r i g h t O b j e c t )

{

/ / С р а в н е н и е т е к у щ е г о S t u d e n t ( н а з о в е м е г о л е в ы м ) и

/ /

д р у г о г о ( н а з о в е м е г о п р а в ы м ) и г е н е р а ц и я о ш и б к и ,

/ /

е с л и э т и о б ъ е к т ы — н е S t u d e n t

S t u d e n t

l e f t S t u d e n t

=

t h i s ;

i f

( ! ( r i g h t O b j e c t i s

S t u d e n t ) )

{

 

 

 

 

 

C o n s o l e . W r i t e L i n e ( " К о м п а р а т о р у п е р е д а н н е S t u d e n t " )

 

r e t u r n

0 ;

 

 

}

 

 

 

 

S t u d e n t r i g h t S t u d e n t =

( S t u d e n t ) r i g h t O b j e c t ;

/ / Г е н е р и р у е м - 1 , 0 и л и 1 н а о с н о в а н и и к р и т е р и я

/ / с о р т и р о в к и

 

 

i f

( r i g h t S t u d e n t . G r a d e

< l e f t S t u d e n t . G r a d e )

{

 

 

 

 

 

r e t u r n

- 1 ;

 

 

}

 

 

 

 

i f

( r i g h t S t u d e n t . G r a d e

> l e f t S t u d e n t . G r a d e )

{

r e t u r n

1 ;

 

 

 

 

 

r e t u r n 0 ,

}

/ / Р е а л и з а ц и я и н т е р ф е й с а I D i s p l a y a b l e :

/ / G e t S t r i n g - в о з в р а щ а е т с т р о к о в о е п р е д с т а в л е н и е / / и н ф о р м а ц и и о с т у д е н т е

p u b l i c s t r i n g G e t S t r i n g О

{

s t r i n g s P a d N a m e = N a m e . P a d R i g n t ( У ) ;

 

s t r i n g

s

=

S t r i n g . F o r m a t ( " { o } :

{ l : N 0 } " ,

 

 

 

 

 

 

s P a d N a m e , G r a d e )

 

r e t u r n

s ;

 

 

 

 

 

 

 

}

 

 

 

 

 

 

 

 

}

 

 

 

 

 

 

 

 

 

/ /

 

 

 

B i r d s - с о р т и р о в к а п т и ц п о и м е н а м

 

 

 

 

 

 

/ / B i r d -

j u s t

a n a r r a y o f b i r d n a m e s

 

 

 

c l a s s B i r d

:

I C o m p a r a b l e , I D i s p l a y a b l e

 

 

 

{

 

 

 

 

 

 

 

 

 

 

p r i v a t e

s t r i n g

s N a m e ;

 

 

 

 

/ / К о н с т р у к т о р - и н и ц и а л и з а ц и я о б ъ е к т а B i r d

 

p u b l i c B i r d ( s t r i n g

s N a m e )

 

 

 

{

 

 

 

 

 

 

 

 

 

t h i s . s N a m e = s N a m e ;

 

 

 

}

 

 

 

 

 

 

 

 

 

/ / C r e a t e B i r d L i s t -

в о з в р а щ а е т с п и с о к п т и ц ; д л я простота]

/ / и с п о л ь з у е м ф и к с и р о в а н н ы й с п и с о к

320

Часть V. За базовым ш

s t a t i c s t r i n g [ ]

s B i r d N a m e s =

{ " O r i o l e " ,

" H a w k " , " R o b i n " , " C a r d i n a l " ,

" B l u e j a y " ,

" F i n c h " , " S p a r r o w " } ;

p u b l i c

s t a t i c

B i r d [ ]

C r e a t e B i r d L i s t ( )

{

 

 

 

 

 

B i r d [ ]

 

b i r d s = n e w B i r d [ s B i r d N a m e s . L e n g t h ] ;

' f o r ( i n t i = 0;

i < b i r d s . L e n g t h ; i + + )

{

 

 

 

 

 

b i r d s [ i ]

= n e w B i r d ( s B i r d N a m e s [ i ] ) ;

}

 

 

 

 

 

r e t u r n

b i r d s ;

 

 

/ / Методы

д о с т у п а т о л ь к о д л я ч т е н и я

p u b l i c

s t r i n g N a m e

 

g e t { r e t u r n s N a m e ;

}

/ /

Р е а л и з а ц и я и н т е р ф е й с а I C o m p a r a b l e :

/ /

C o m p a r e T o - с р а в н е н и е и м е н п т и ц ; и с п о л ь з у е т с я

/ /

в с т р о е н н ы й м е т о д с р а в н е н и я к л а с с а S t r i n g

p u b l i c i n t C o m p a r e T o ( o b j e c t r i g h t O b j e c t )

{

/ / С р а в н е н и е т е к у щ е г о B i r d ( н а з о в е м е г о л е в ы м ) и

/ / д р у г о г о ( н а з о в е м е г о п р а в ы м )

B i r d

l e f t B i r d

=

t h i s ;

B i r d

r i g h t B i r d

=

( B i r d ) r i g h t O b j e c t ;

r e t u r n S t r i n g . C o m p a r e ( l e f t B i r d . N a m e , r i g h t B i r d . N a m e ) ;

/ / Р е а л и з а ц и я и н т е р ф е й с а I D i s p l a y a b l e :

/ / G e t S t r i n g - в о з в р а щ а е т с т р о к у с и м е н е м п т и ц ы p u b l i c s t r i n g G e t S t r i n g ( )

{

r e t u r n Name,-

Класс S t u d e n t (примерно в середине листинга) реализует интерфейсы I C o m p a r a ­ ble и I D i s p l a y a b l e , как описано ранее. Метод C o m p a r e T o О сравнивает студентов юуспеваемости, что приводит к соответствующей сортировке их списка. Метод G e t ­ String () возвращает имя и успеваемость студента.

Прочие методы класса S t u d e n t включают свойства только для чтения Name и G r a d e , простой конструктор и метод C r e a t e S t u d e n t L i s t ( ) . Последний метод просто возвра-

<ает фиксированный список студентов.

 

 

Класс B i r d внизу листинга

также реализует

интерфейсы I C o m p a r a b l e

и I D i s ­

playable. Он реализует метод

C o m p a r e T o ( ) ,

который сравнивает названия птиц по­

средством встроенного метода

сравнения класса

S t r i n g . Таким образом, в

результате

сортировки получается список птиц в алфавитном порядке. Метод G e t N a m e () просто Извращает название птицы .

[(лава 14. Интерфейсы и структуры

321

Теперь можно вернуться к функции M a i n () . Метод C r e a t e S t u d e n t L i s t ( ) и с пользуется для получения несортированного списка, который сохраняется в массиве s t u d e n t s .

Обычно для имен коллекций объектов, таких как массивы, используются суще ствительные.

Массив студентов сперва преобразуется в массив c o m p a r a b l e O b j e c t s . Это отли чается от массивов, использованных ранее в этой книге (в основном в главе 6 "Объединение д а н н ы х — классы и массивы") . Эти массивы были массивами объектом

определенного

класса, наподобие массива объектов S t u d e n t , в то

время как compa­

r a b l e O b j e c t s

представляет собой массив объектов, реализующих

интерфейс ICom­

p a r a b l e безотносительно к классу, которому принадлежат объекты. Использование ин терфейса в качестве типа элементов массива, типа параметра или возвращаемого значе­

ния — м о щ н ы й метод повышения гибкости программы .

 

Массив c o m p a r a b l e O b j e c t s передается встроенному

методу A r r a y . Sort ( ) ,

который и сортирует студентов по их успеваемости.

 

Затем отсортированный массив объектов типа S t u d e n t

передается локально опре­

деленному методу D i s p l a y A r r a y ( ) , итеративно проходящему по всем элементам массива объектов, которые реализуют метод G e t S t r i n g ( ) . Для выяснения количества элементов массива используется свойство A r r a y . L e n g t h . Затем для каждого объекта вызывается метод G e t S t r i n g ( ) , и его результат выводится на дисплей с помощью функции W r i t e L i n e ( ) .

Далее программа сортирует и выводит список птиц. Несомненно, вы согласитесь, что между птицами и студентами нет ничего общего. Однако класс B i r d реализует интер­ фейс I C o m p a r a b l e путем сравнения названий птиц и интерфейс I D i s p l a y a b l e пу тем возврата названий птиц.

Обратите внимание, что функция M a i n () не выполняет преобразования типа массива птиц — в этом нет необходимости. Это аналогично следующему фрагменту исходного текста:

c l a s s B a s e C l a s s

{ }

c l a s s S u b c l a s s

: B a s e C l a s s { }

c l a s s P r o g r a m

 

{

p u b l i c p u b l i c

s t a t i c v o i d S o m e F u n c t i o n ( B a s e C l a s s b e )

{ }

s t a t i c v o i d A n o t h e r F u n c t i o n ( )

 

{

 

S u b c l a s s

s c

= n e w S u b c l a s s ( ) ;

 

 

 

 

 

 

S o m e F u n c t i o n ( s c ) ;

 

 

 

 

 

 

Здесь

объект

класса S u b c l a s s может быть передан

как объект

B a s e C l a s s , по­

скольку

S u b c l a s s

Я В Л Я Е Т С Я

B a s e C l a s s .

 

 

 

 

 

Аналогично, массив объектов

B i r d может быть передан методу,

ожидающему мас

сив

объектов I C o m p a r a b l e , поскольку класс

B i r d реализует интерфейс

ICompara­

b l e .

Следующий

в ы з о в — D i s p l a y A r r a y ( )

— также

получает

массив

b i r d s б е з

преобразования типа, поскольку класс B i r d s реализует интерфейс

I D i s p l a y a b l e .

Вывод программы выглядит следующим образом:

 

 

 

 

Часть V. За базовыми классами

Сортировка

с п и с к а

с т у д е н т о в

Lisa

:

1 0 0

 

Marge

:

85

 

Bart

:

50

 

Maggie

:

3 0

 

Homer

:

0

 

Сортировка

с п и с к а

п т и ц

Blue j a y

 

 

 

Cardinal

 

 

 

I Finch

 

 

 

Hawk

Oriole

Robin Sparrow

Нажмите < E n t e r > д л я з а в е р ш е н и я п р о г р а м м ы . . . "

И студенты, и птицы отсортированы, каждый список — в соответствии со своим кри­ терием сортировки.

Интерфейс может "наследовать" методы другого интерфейса. Я использую кавычки, поскольку это не истинное наследование, независимо от того, как оно выглядит. В при­ веденном далее фрагменте кода перечислены базовые интерфейсы, что очень напомина­ ет указание базового класса.

/ / I C o m p a r e - и н т е р ф е й с , к о т о р ы й м о ж е т к а к с р а в н и в а т ь / / о б ъ е к т ы , т а к и в ы в о д и т ь и н ф о р м а ц и ю о с в о е м з н а ч е н и и p u b l i c i n t e r f a c e I C o m p a r e : I C o m p a r a b l e

{

/ / G e t V a l u e - в о з в р а щ а е т с о б с т в е н н о е ц е л о е з н а ч е н и е i n t G e t V a l u e ( ) ;

Интерфейс I C o m p a r e наследует требования по реализации C o m p a r e T o () от интерфей­ са I C o m p a r a b l e . К этому добавляется требование о реализации метода G e t V a l u e ( ) . Объ­ ект I C o m p a r e может использоваться в качестве объекта I C o m p a r a b l e , поскольку по опре­ делению он реализует его требования. Однако это не полное наследование в объектноориентированном С#-смысле этого слова. Здесь невозможен никакой полиморфизм. Кроме того, здесь неприменимы обычные отношения между конструкторами.

Наследование интерфейсов будет проиллюстрировано в демонстрационной програм­ ме A b s t r a c t l n t e r f а с е в следующем разделе.

Для реализации интерфейса класс должен реализовать все его методы. Од­ нако класс может реализовать метод интерфейса как абстрактный метод (само собой, такой класс является абстрактным), как, например, в приведен­ ной далее демонстрационной программе .

Глава 14. Интерфейсы и структуры

323

/ /

A b s t r a c t l n t e r f а с е - д е м о н с т р и р у е т р е а л и з а ц и ю и н т е р ф е й с а

/ /

а б с т р а к т н ы м к л а с с о м

u s i n g

S y s t e m ;

n a m e s p a c e

A b s t r a c t l n t e r f а с е

{

 

 

/ / I C o m p a r e - и н т е р ф е й с , к о т о р ы й м о ж е т к а к с р а в н и в а т ь

/ / о б ъ е к т ы , т а к и в ы в о д и т ь с о б с т в е н н о е з н а ч е н и е

p u b l i c i n t e r f a c e I C o m p a r e : I C o m p a r a b l e

/ / G e t V a l u e - в о з в р а щ а е т с о б с т в е н н о е з н а ч е н и е к а к i n t

i n t G e t V a l u e ( ) ;

}

/ / B a s e C l a s s - р е а л и з у е т и н т е р ф е й с I C o m p a r e , р е а л и з у я / / к о н к р е т н ы й м е т о д G e t V a l u e ( ) и а б с т р а к т н ы й м е т о д

/ / C o m p a r e T o ( )

 

a b s t r a c t p u b l i c c l a s s

B a s e C l a s s : I C o m p a r e

{

 

i n t n V a l u e ;

 

p u b l i c B a s e C l a s s ( i n t

n l n i t i a l V a l u e )

{

 

n V a l u e = n l n i t i a l V a l u e ;

}

 

/ / Р е а л и з а ц и я и н т е р ф е й с а I C o m p a r e : / / с н а ч а л а к о н к р е т н ы й м е т о д

p u b l i c i n t G e t V a l u e ( )

{

r e t u r n n V a l u e ;

}

/ / а з а т е м р е а л и з у е т и н т е р ф е й с I C o m p a r e п р и п о м о щ и

? 7 а о с т р а к т н о т о м е ' т о д а

a b s t r a c t p u b l i c i n t C o m p a r e T o ( o b j e c t r i g h t O b j e c t ) ;

/ / S u b c l a s s - З а в е р ш а е т б а з о в ы й к л а с с п у т е м п е р е к р ы т и я / / а б с т р а к т н о г о м е т о д а C o m p a r e T o О

p u b l i c c l a s s S u b c l a s s :

B a s e C l a s s

 

 

^ / / П е р е д а е м з н а ч е н и е , п о л у ч е н н о е к о н с т р у к т о р о м ,

/ / к о н с т р у к т о р у б а з о в о г о к л а с с а

 

 

p u b l i c S u b c l a s s ( i n t

n l n i t i a l V a l u e )

:

b a s e ( n l n i t i a l V a l u e )

{

 

 

 

 

 

}

 

 

 

 

 

// C o m p a r e T o

-

реализует

интерфейс

 

IComparable;

I I в о з в р а щ а е т у к а з а н и е , б о л ь ш е л и о д и н о б ъ е к т п о д к л а с с а

/ / д р у г о г о и л и н е т

 

 

 

 

o v e r r i d e p u b l i c

i n t

C o m p a r e T o ( o b j e c t

r i g h t O b j e c t )

324

Часть V. За базовыми классам

Глава 1

B a s e C l a s s b e

= ( B a s e C l a s s ) r i g h t O b j e c t ;

r e t u r n G e t V a l u e ( ) . C o m p a r e T o ( b e . G e t V a l u e ( ) ) ;

public c l a s s P r o g r a m

p u b l i c s t a t i c

v o i d M a i n ( s t r i n g [ ] s t r i n g s )

S u b c l a s s s c l = n e w S u b c l a s s ( 1 0 ) ;

S u b c l a s s s c 2

= n e w S u b c l a s s ( 2 0 ) ;

MyFunc ( s c l ,

s c 2 ) ,-

/ / О ж и д а е м п о д т в е р ж д е н и я п о л ь з о в а т е л я

C o n s o l e . W r i t e L i n e ( " Н а ж м и т е < E n t e r > д л я " +

" з а в е р ш е н и я п р о г р а м м ы . . . " ) ;

C o n s o l e . R e a d ( ) ;

}

/ / MyFunc - и с п о л ь з у е т

м е т о д ,

п р е д о с т а в л е н н ы й

/ / и н т е р ф е й с о м I C o m p a r e д л я в ы в о д а з н а ч е н и й д в у х

/ / о б ъ е к т о в и у к а з а н и я , к а к о й и з н и х б о л ь ш е

p u b l i c s t a t i c v o i d M y F u n c ( I C o m p a r e i c l ,

I C o m p a r e i c 2 )

{

 

 

 

C o n s o l e . W r i t e L i n e ( " З н а ч е н и е i c l р а в н о { 0 } , " +

" a

i c 2 -

{ l } " ,

 

i c l . G e t V a l u e ( ) , i c 2

. G e t V a l u e ())•;

string s;

switch ( i c l . C o m p a r e T o ( i c 2 ) )

{

c a s e

0 :

s =

" р а в е н " ;

b r e a k ;

c a s e

- 1 :

s = " м е н ь ш е " ;

b r e a k ;

c a s e

1 :

s = " б о л ь ш е " ;

d e f a u l t :

s = " н е п о н я т н о " ; b r e a k ;

}

Console . W r i t e L i n e

(

" О б ъ е к т i c l

{ o } о б ъ е к т а i c 2 " . s ) ;

fma 14. Интерфейсы и структуры

325

И н т е р ф е йс I C o m p a r e описывает класс, который может сравнивать два объекта и по лучать их значения. I C o m p a r e наследует требование реализации C o m p a r e T o () от терфейса I C o m p a r a b l e , а кроме того, добавляет собственный метод G e t V a l u e (), торый возвращает целочисленное значение объекта.

Несмотря

на то что метод может вернуть значение объекта как i n t , GeT

V a l u e ()

ничего не говорит о внутреннем устройстве класса. Генерация™

целого значения может потребовать проведения сложных вычислений.

Класс B a s e C l a s s реализует интерфейс I C o m p a r e — конкретный метод GetValue

возвращает значение члена n V a l u e . Однако метод C o m p a r e T o ( ) , требуемый интерфейса I C o m p a r e , объявлен как абстрактный.

Объявление класса a b s t r a c t означает, что в нем отсутствует реализация одной или нескольких с в о й с т в — в рассматриваемом случае метода C o m p a r e T o ( ) . Р е лизация этого метода отложена до подкласса данного абстрактного класса.

S u b c l a s s

реализует

метод C o m p a r e T o ( ) , что необходимо для

того, чтобы э т о т

класс был конкретным .

 

 

 

 

 

 

 

 

Заметим, что

S u b c l a s s

автоматически реализует

интерфейс

ICompare не

 

смотря на то,

что это не сказано явно. B a s e C l a s s

обещает реализовать методы

 

I C o m p a r e , a S u b c l a s s

Я В Л Я Е Т С Я B a s e C l a s s . Наследуя

эти методы, Sub

 

C l a s s автоматически удовлетворяет требованиям по реализации

ICompare .

Функция M a i n ()

создает

два

объекта

класса S u b c l a s s

с различными значениям

а затем передает их функции

M y F u n c ( ) .

Метод M y F u n c ()

ожидает получения двух

объектов

с

интерфейсом

I C o m p a r e .

Функция M y F u n c ()

использует метод

C o m p a r e T o ()

для принятия решения о том, какой из объектов больше, а затем приме

няет метод G e t V a l u e

()

для вывода " з н а ч е н и й " этих двух объектов.

 

 

Вывод этой программы достаточно короток:

 

 

 

З н а ч е н и е i c l р а в н о 1 0 ,

a i c 2 — 2 0

 

 

 

О б ъ е к т

i c l м е н ь ш е о б ъ е к т а

i c 2

 

 

 

 

Н а ж м и т е < E n t e r > д л я з а в е р ш е н и я п р о г р а м м ы . . .

Из главы 15, "Обобщенное программирование", вы узнаете, как можно писать обобщенные интерфейсы.

С# обладает определенной дихотомией при объявлении переменных. Вы объявляете и инициализируете переменные типов-значений, таких как i n t или d o u b l e , следующим

образом:

 

i n t п ;

/ / О б ъ я в л е н и е

n = 1;

// И н и ц и а л и з а ц и я

326

Часть V. За базовыми классам»

Однако ссылки на объекты вы объявляете и инициализируете совершенно иначе:

public

c l a s s

M y C l a s s

p u b l i c

i n t

n ;

 

 

MyClass

m c ;

 

 

/ / О б ъ я в л е н и е

mc = new

M y C l a s s () ;

// И н и ц и а л и з а ц и я

 

Переменная

mc

имеет ссылочный тип, поскольку она ссылается на потенци­

 

ально удаленную

память. Встроенные переменные типа i n t или d o u b l e из­

 

вестны

как

переменные типов-значений.

Если вы посмотрите на п или тс более пристально, то увидите, что единственное ре­ альное отличие состоит в том, что С# выделяет память для переменных типов-значений автоматически, в то время как для объектов классов вы д о л ж н ы выделять память явно . Интересно, нельзя ли объединить их посредством некоторой Единой Теории Классов?

Структуры С #

С# определяет третий тип переменных, именуемый структурой, который представ­ ляет собой мост через пропасть между ссылочными типами и типами-значениями. Син­ таксис объявления структуры выглядит почти так же, как и у класса:

public struct

M y S t r u c t

p u b l i c

i n t

n ;

 

p u b l i c d o u b l e

d ;

public c l a s s

M y C l a s s

p u b l i c

i n t

n ;

 

p u b l i c d o u b l e

d ;

Обращение к объекту структуры осуществляется так же, как и к объекту класса, но выделение памяти — как для типа-значения, что демонстрируется следующим кодом:

// Объявление

и

д о с т у п

к п р о с т о м у т и п у - з н а ч е н и ю

 

int

П ;

 

 

 

 

 

 

 

n = 1;

 

 

 

 

 

 

 

/ /

Объявление

с т р у к т у р ы

п о х о ж е

н а о б ъ я в л е н и е

п р о с т о г о

i n t

MyStruct

m s ;

/ /

А в т о м а т и ч е с к о е

в ы д е л е н и е п а м я т и

 

ms.n

= 3 ;

/ /

Д о с т у п

к ч л е н а м

в ы п о л н я е т с я

т а к ж е ,

к а к и

ins.d

= 3

. 0 ;

/ /

д л я о б ъ е к т а к л а с с а

 

 

//Память для объекта класса должна быть выделена в

//отдельной области при помощи оператора new

MyClass

mc

= n e w M y C l a s s ;

men =

2 ;

 

mc.d =

2 . 0

;

Объект s t r u c t хранится в памяти так же, как и переменные встроенных типов. Пе­ ременная ms не является ссылкой на некоторый блок внешней памяти, выделенный в от­ дельной области. Объект ms занимает память в той же области, что и переменная п, как показано на рис. 14.1.

km 14. Интерфейсы и структуры

327

Рис. 14.1. Структурная переменная ms "живет"

втой же области памяти, что и переменная п,

вто время как память для объекта тс выделя­ ется в отдельной области памяти

Отличие между ссылками и типами-значениями еще более очевидно в следующее примере. Создание массива из 100 ссылочных объектов требует от программы 101 вызов оператора new (один для массива и по одному для каждого объекта):

M y C l a s s [ ] mc = new M y C l a s s [ 1 0 0 ] ;

f o r ( i n t i = 0; i < m s . L e n g t h ; i + + )

{

mc [ i ] = new M y C l a s s ( ) ;

}

m c [ 0 ] . n = 0;

Массив также приводит к определенным накладным расходам, как в смысле времеyb работы, так и используемой памяти.

Каждый элемент в массиве тс должен быть достаточно большим, чтобы содер­ жать ссылку на объект.

Каждый объект M y C l a s s имеет невидимые накладные расходы памяти до и после единственного члена-данных п.

При рассмотрении времени работы программы следует учесть, что она должна 100 раз выделить область памяти, а обращение к элементу массива требует двух обращений к ссылкам — ссылке на массив и ссылке в соответствующем элементе массива.

Память для объекта структуры выделяется сразу, как для части массива:

/ / О б ъ я в л е н и е м а с с и в а i n t

 

 

 

i n t [ ]

i n t e g e r s

=

new i n t [ 1 0 0 ] ;

/ /

Выделение

п а м я т и

i n t e g e r s [ 0 ]

= 0;

 

 

 

 

/ / О б ъ я в л е н и е м а с с и в а с т р у к т у р т а к о е ж е п р о с т о е

 

M y S t r u c t [ ]

ms

=

new M y S t r u c t [ 1 0 0 ] ;

//

Выделение

п а м я т и

ms [ 0]

. n =

0;

 

 

 

 

 

В этом случае выделяется один большой блок памяти.

328

Часть V. За базовыми классами

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]