Синтаксис

Язык Visual Basic на платформе .NET.

Модераторы: Ramzes, Sebas

Hexen
Начинающий
Начинающий
 
Сообщения: 7
Зарегистрирован: 30.03.2004 (Вт) 15:37

Синтаксис

Сообщение Hexen » 30.03.2004 (Вт) 16:10

Здравствуйте уважаемые программеры.
Я пишу библиотеку на VB.NET и столкнулся проблемой.
Мне нужно спрятать функцию базового класса, которая была объявлена как Public.
Пример:
Код: Выделить всё
Imports System.Console

Friend Class Class1
    Public Sub fn()
        WriteLine("Class 1 fn")
    End Sub
End Class

Public Class Class2
    Inherits Class1
    Private Shadows Sub fn()
        MyBase.fn()
        WriteLine("Class 2 fn")
    End Sub
    Public Sub fn2()
        WriteLine("Class 2 fn2")
    End Sub
End Class

Module Module1
    Sub Main()
        Dim a As New Class2
        a.fn() 'по идеи сдесь должна быть ошибка
        a.fn2()
    End Sub
End Module

По идеи функция fn объекта a не должна вызываться, но вызывается функция базового класса. Результат:
    Class 1 fn
    Class 2 fn2
Как запретить вызов fn из производного класса?
Сделал тоже самое на С++:
Код: Выделить всё
__gc class CClass1
{
public:
   void fn()
   {
      Console::WriteLine(S"Class 1");
   }
};
__gc class CClass2: public CClass1
{
private:
   void fn()
   {
      Console::WriteLine(S"Class 2");
   }
public:
   void fn2()
   {
      Console::WriteLine(S"Class 2: fn2");
   }
};
int _tmain()
{
    // TODO: Please replace the sample code below with your own.
    CClass2 *a = new CClass2;
   a->fn(); //компилятор это место не проходит
   a->fn2();
   return 0;
}

Все как надо.

Может я какое-нибуть слово не знаю?

Грандж
Продвинутый пользователь
Продвинутый пользователь
 
Сообщения: 150
Зарегистрирован: 29.10.2002 (Вт) 14:10
Откуда: Москва

Сообщение Грандж » 30.03.2004 (Вт) 17:56

вообще, с подобного рода продуманной инкапсуляцией сталкиваюсь впервые. Типа ну и могу ошибаться, но попробуй в отнаследованном классе поставить Protected.

вообще, все тонкости инкапсуляции описаны в книгах "Переход на VB .net:Стратегии, концепции, код"(Дэн Эпплман), "Программирование на VB .net" (кто написал не помню, зелёная такая) Обе издательства "ПИТЕР".

под рукой нет ни книг ни басика - посмотреть не могу %(
и между ног затеплилась надежда
(%

http://grunger.net.ru

Hexen
Начинающий
Начинающий
 
Сообщения: 7
Зарегистрирован: 30.03.2004 (Вт) 15:37

Сообщение Hexen » 31.03.2004 (Ср) 8:27

Сама проблема заключается в том, что я должен обеспечить правильность работы библиотеки, а также легкость понимания её логики. Мои классы являются посредниками, они накладывают более строгие правила работы с другой библиотекой, тем самым гарантируя правильный подход к процессам. Но при таком выпендреже Basic-а у меня ничего не получается. Единственный способ закрыть функцию базового класса (который я нашел) это ее полностью переопределить и оставить пустой:
Код: Выделить всё
Public Class Class2
    Inherits Class1
    Public Shadows Sub fn()

    End Sub
...
End Class

Но тогда все равно остается ошметок, функция которая ничего не вызывает.
Я попробовал хотя бы документировать это так, как это делается в C#, при помощи <summary>, но это в VB.NET тоже не работает (Все таки интересно, а возможно это в VB.NET вообще).

Грандж
Продвинутый пользователь
Продвинутый пользователь
 
Сообщения: 150
Зарегистрирован: 29.10.2002 (Вт) 14:10
Откуда: Москва

Сообщение Грандж » 01.04.2004 (Чт) 16:25

vs.net сказал:
Public Class cannot inherit from a Friend Class because it expands the access of the base Class.

/; непонятно чего-то.. у тебя vs какой?
и между ног затеплилась надежда
(%

http://grunger.net.ru

Hexen
Начинающий
Начинающий
 
Сообщения: 7
Зарегистрирован: 30.03.2004 (Вт) 15:37

Сообщение Hexen » 01.04.2004 (Чт) 17:03

Точнее говоря класс CClass1 должен иметь Public. Ошибся когда правил код после экспериментов :wink: .
Правильный код:
Код: Выделить всё
Imports System.Console

Public Class Class1
    Public Sub fn()
        WriteLine("Class 1 fn")
    End Sub
End Class

Public Class Class2
    Inherits Class1
    Private Shadows Sub fn()
        MyBase.fn()
        WriteLine("Class 2 fn")
    End Sub
    Public Sub fn2()
        WriteLine("Class 2 fn2")
    End Sub
End Class

Module Module1
    Sub Main()
        Dim a As New Class2
        a.fn() 'по идеи здесь должна быть ошибка
        a.fn2()
    End Sub
End Module

Результат:
    Class 1 fn
    Class 2 fn2
Вообще, как я увидел понятия наследования в обычном С++ и в .NET (VB и C#) отличаются, отличается и его применение. В этом и заключаются мои непонятки. В .NET, по моему, его концепция немного корявая или я чего-то не до понимаю.
Для примера рассмотрим класс System.Collections.CollectionBase. Его предлагают как базовый для создания своих коллекций. Но если посмотреть на его структуру, то мы увидим что он включает в себя объект InnerList от класса ArrayList
Код: Выделить всё
Protected ReadOnly Property InnerList As ArrayList

и идет переписывание всех функций заново. Мне кажется что если бы в .NET сделали такое же наследование как и в обычном С++, то заморочек было бы меньше (ну можно запретить множественное наследование). В книге Дан Эпплман "Переход на VB.NET. Стратегии, концепции, код." Говорится, что наследование в VB.NET позволяет более эффективнее использовать код. Но мне кажется, что здесь надо добавить слово "чуть-чуть".

Грандж
Продвинутый пользователь
Продвинутый пользователь
 
Сообщения: 150
Зарегистрирован: 29.10.2002 (Вт) 14:10
Откуда: Москва

Сообщение Грандж » 01.04.2004 (Чт) 20:10

Код: Выделить всё
Imports System.Console

Public Class Class1
    Protected Sub fn()
        WriteLine("Class 1 fn")
    End Sub
End Class

Public Class Class2
    Inherits Class1
    Private Shadows Sub fn()
        MyBase.fn()
        WriteLine("Class 2 fn")
    End Sub
    Public Sub fn2()
        WriteLine("Class 2 fn2")
    End Sub
End Class

Module Module1
    Sub Main()
        Dim a As New Class2
        a.fn2()
    End Sub
End Module


всё пашет[/code]
и между ног затеплилась надежда
(%

http://grunger.net.ru

Hexen
Начинающий
Начинающий
 
Сообщения: 7
Зарегистрирован: 30.03.2004 (Вт) 15:37

Сообщение Hexen » 02.04.2004 (Пт) 8:44

Так в том то и дело, что не должно.
Ну для примера:
Мне дана библиотека для работы с EDIFACT форматом данных.
У него есть проперть InterchangeControlReference, которая принимает строку длиной 14 символов.

Код: Выделить всё
Public Property InterchangeControlReference() as String


Системам LORS накладывает свои правила: использовать только первые 8 символов и они должны быть только числами.
Ну тут еще и заказчик накладывает свои требования:
первые четыре символа ID компании, остальные разбиваются на два поля и в водятся из соображений юзера. При чем в этой библиотеке есть функция
Код: Выделить всё
Public Sub Clean()

которую мне нужно спрятать чтобы другие разработчики ею не воспользовались и не нарушили логику работы моей библиотеке.

С требованием LORS справляемся просто:
Код: Выделить всё
Public Shadows Property InterchangeControlReference() as String


С требованием клиента тоже. Хотя VB.NET уже начинает тебя ограничивать. Мы не можем просто закрыть старую проперть и обозвать поля своими именами. VB.NET заставляет переопределить старую пропеть. И нельзя закрыть функцию Clean()
Код: Выделить всё
Private Shadows Sub Clean()

потому, что при создании объекта из моей библиотеке и вызова функции Clean() не будет дано сообщение о том что данная функция является Private в данном классе, а будет вызвана функция базового класса(как было показано в примере).

Грандж
Продвинутый пользователь
Продвинутый пользователь
 
Сообщения: 150
Зарегистрирован: 29.10.2002 (Вт) 14:10
Откуда: Москва

Сообщение Грандж » 02.04.2004 (Пт) 15:01

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

если нет, придёцца оставлять пустую функцию.
не постил ничего на буржуйские конференции?
и между ног затеплилась надежда
(%

http://grunger.net.ru

Hexen
Начинающий
Начинающий
 
Сообщения: 7
Зарегистрирован: 30.03.2004 (Вт) 15:37

Сообщение Hexen » 02.04.2004 (Пт) 15:23

Нет.
Да и смысла нету. В .NET нет того наследования как и в С++ :cry: .
Доказательством является пример из MSDN про класс System.Collections.CollectionBase. Класс содержит в себе объект класса System.Collections.ArrayList и вся работа с коллекцией сводиться с работой с этим классом. Но вот что интересно, что бы скрыть некоторые функции класса ArrayList, а другие сделать Protected, они не связываются с наследием, а делают ArrayList членом класса CollectionBase и упорно переписывают все функции. Ну если это делает Microsoft, то и нам наверное придется, но нам за это не платят.

Грандж
Продвинутый пользователь
Продвинутый пользователь
 
Сообщения: 150
Зарегистрирован: 29.10.2002 (Вт) 14:10
Откуда: Москва

Сообщение Грандж » 02.04.2004 (Пт) 16:55

обидно /;
ты хотел сделать пустую процедуру.. это конечно криво, но зато меньше усилий нужно приложить
и между ног затеплилась надежда
(%

http://grunger.net.ru


Вернуться в Visual Basic .NET

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 71

    TopList