Re[4]: [ООП] Хочу странного
От: VladD2 Российская Империя www.nemerle.org
Дата: 08.03.10 21:05
Оценка:
Здравствуйте, AndrewVK, Вы писали:

AVK>Я, честно говоря, мог попутать Go с чем то еще на гугле. В том языке, про который речь, вроде бы были встроенные в него миксины.


Интересно с чем? В Гоу вроде бы их не было. Хотя может это я ошибаюсь.
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re: [ООП] Хочу странного
От: LordMAD Россия  
Дата: 09.03.10 07:52
Оценка:
Здравствуйте, 0x7be, Вы писали:

0>Что если принципиально разделить эти вещи? Абстракция через обобщение в чистом виде есть во многих языка в виде интерфейсов, которые, кстати, поддерживают множественное наследование даже там, где классы поддерживают только единичное. Повторное использование кода тоже возможно другим способом — через композицию объектов. Единственное, чего нет — это синтаксически хорошо оформленное делегирование реализации интерфейса/части интерфейса композитам, из которых составлен класс-композиция. Но это не сложный аспект, который можно реализовать.


Тот же delphi поддерживает implementing interfaces by delegation c 1998 года (с delphi 4.0). Аналогичную возможность обещали в c# 4.0
Re: [ООП] Хочу странного
От: FR  
Дата: 09.03.10 08:34
Оценка: 16 (1)
Здравствуйте, 0x7be, Вы писали:


0>Что если принципиально разделить эти вещи? Абстракция через обобщение в чистом виде есть во многих языка в виде интерфейсов, которые, кстати, поддерживают множественное наследование даже там, где классы поддерживают только единичное. Повторное использование кода тоже возможно другим способом — через композицию объектов. Единственное, чего нет — это синтаксически хорошо оформленное делегирование реализации интерфейса/части интерфейса композитам, из которых составлен класс-композиция. Но это не сложный аспект, который можно реализовать.


В D http://www.digitalmars.com/d/2.0/index.html все это уже есть, интерфейсы, множественного наследования реализации нет, но есть миксины http://www.digitalmars.com/d/2.0/mixin.html и очень мощное делегирование в виде http://www.digitalmars.com/d/2.0/class.html#AliasThis и http://www.digitalmars.com/d/2.0/operatoroverloading.html#Dispatch

В язках с утиной типизацией классов, например питон и ocaml тоже самое легко реализуется без подобных дополнительных фишек.
Re[2]: [ООП] Хочу странного
От: FR  
Дата: 09.03.10 08:38
Оценка:
С миксинами чуть промахнулся http://www.digitalmars.com/d/2.0/template-mixin.html
Re[4]: [ООП] Хочу странного
От: FR  
Дата: 09.03.10 08:41
Оценка:
Здравствуйте, AndrewVK, Вы писали:

AVK>Я, честно говоря, мог попутать Go с чем то еще на гугле. В том языке, про который речь, вроде бы были встроенные в него миксины.


Скорее всего с D попутал.
Re[5]: [ООП] Хочу странного
От: AndrewVK Россия http://blogs.rsdn.org/avk
Дата: 09.03.10 10:37
Оценка:
Здравствуйте, FR, Вы писали:

FR>Скорее всего с D попутал.


В D нет наследования реализации?
... << RSDN@Home 1.2.0 alpha 4 rev. 1464 on Windows 7 6.1.7600.0>>
AVK Blog
Re[2]: [ООП] Хочу странного
От: AndrewVK Россия http://blogs.rsdn.org/avk
Дата: 09.03.10 10:37
Оценка:
Здравствуйте, LordMAD, Вы писали:

LMA>Тот же delphi поддерживает implementing interfaces by delegation c 1998 года (с delphi 4.0).


Только для СОМ.
... << RSDN@Home 1.2.0 alpha 4 rev. 1464 on Windows 7 6.1.7600.0>>
AVK Blog
Re[6]: [ООП] Хочу странного
От: FR  
Дата: 09.03.10 10:43
Оценка:
Здравствуйте, AndrewVK, Вы писали:

FR>>Скорее всего с D попутал.


AVK>В D нет наследования реализации?


Одиночное есть, множественного нет, для интерфейсов множественное есть.
Но при тех средствах что в нем доступны миксины, алиасы this и диспетчеризации вызовов, можно при желании легко обойтись без наследования вообще
Re[7]: [ООП] Хочу странного
От: AndrewVK Россия http://blogs.rsdn.org/avk
Дата: 09.03.10 10:55
Оценка:
Здравствуйте, FR, Вы писали:

FR>Одиночное есть, множественного нет, для интерфейсов множественное есть.


Речь про то, чтобы наследование реализации совсем убрать. Любое.
... << RSDN@Home 1.2.0 alpha 4 rev. 1464 on Windows 7 6.1.7600.0>>
AVK Blog
Re[2]: [ООП] Хочу странного
От: Воронков Василий Россия  
Дата: 09.03.10 11:00
Оценка: +1
Здравствуйте, Caracrist, Вы писали:

C>Пишешь такие методы на интерфейсы и наследуешь сколько хочешь и по сколько хочешь раз.


Extensions Methods — это синтаксический сахар, *весь* смысл которого заключается в том, что он позволяет вместо

MyHelper.DoSomething(foo);


писать

foo.DoSomething();


При этом DoSomething по-прежнему внешний статический метод, не имеющий доступа к деталям реализации Foo, а со структурами вы так еще и лишнее копирование получите.
Причем у Extensions Methods есть и немало минусов — например, очень плохо discoverability функциональности.
Re[8]: [ООП] Хочу странного
От: FR  
Дата: 09.03.10 11:06
Оценка:
Здравствуйте, AndrewVK, Вы писали:

AVK>Речь про то, чтобы наследование реализации совсем убрать. Любое.


В том D который есть сейчас это вполне реально, во всяком случае писание в таком стиле
никаких неудобств не вызовет.
Re[6]: [ООП] Хочу странного
От: fmiracle  
Дата: 09.03.10 13:02
Оценка: 4 (1)
Здравствуйте, Yuki-no Tenshi, Вы писали:

0>>Вот и я о том же. Но если ручное делегирование заменить специальным механизмом, позволяющим делегировать композиту реализацию интефеса/его части, то подобной проблемы не будет.


YNT>Можно пример( допустим, на некоем псевдокоде) работы описанного вами механизма? Или это утверждение что-то вроде "хорошо бы чтобы был мир во всем Мире"


Если я правильно понял чего хочет автор, то это действительно старая шировко известная в узких кругах вещь (потому, думаю и не пошла пока в широкие массы, что про аггрегацию и делегирование ширпотребных книг мало, а про наследование — в любом учебнике "С? за пять дней")

И выглдяит желаемое примерно так:


interface IVehile
{
   void Move();
}
interface IGun
{
   void Fire();
}

class Car : IVehile
{
  public void Move()
  {
    //some implementation
  }
  
  public void OtherMethod(){}
  public void AndOneMoreNotIntrestingMethod(){}
}

class Gun : IGun
{
  public void Fire()
  {
     //some implementation
  }
}

public class Tank: IVehile, IGun
{
   [TakeMethod( Move )]
     private Car _chassis;  //теперь у класса Tank есть собственный метод Move, взятый из класса Car. Можно вызывать tank.Move();
     
     [TakeMethod( Fire )]
     private Gun _gun;       //теперь у класса Tank есть собственный метод Fire, взятый из класса Gun. Можно вызывать tank.Fire();
     
     //но можно комбинировать и не напряму, а как в обычной агрегации
     public void LocateAndDestroy()
     {
            //IsTargetLocated & SearchTarget - реализованы тоже в этом классе каким-то там способом,
            // включая возможное собственное внутреннее состояние
            while( !IsTargetLocated )  
            {
                _chassis.Move();
                SearchTarget();
            }
            _gun.Fire();
     }
}

//никто однако не мешает сделать то же и без агрегирования любого из имеющихся объектов
public class LaserTank: IVehile, IGun
{
    [TakeMethod( Move )]
      private Car _chassis;
      
      public void Fire()
      {
         //Implement Laser Fire
      }
}

//или можно использовать метод не целиком как есть а как часть (аналог вызова base.Method):
public class RoadBuildingTank: IVehile, IGun
{
     private Car _chassis;  
     
     [TakeMethod( Fire )]
     private Gun _gun;      
     
     public void Move()
     {
        BuildRoadAtFront();
        _chassis.Move();
        DestroyRoadAtBehind();
     }
}


//одно из очевидных применений передавать объекты-агрегаты как параметры.
//В результате получим динамически создаваемые классы

class Tank : IVehile, IGun
{
   [TakeMethod( Move )]
     private ICar _chassis;  
     
     [TakeMethod( Fire )]
     private IGun _gun;
     
     public Tank( IVehile chassis, IGun gun )
     {
      _chassis = chassis;
      _gun = gun;
     }
}

//использование
var tank = new Tank( new TracksVehile(), new Gun() );
tank.Move();
tank.Fire();
var laserTank = new Tank( new TracksVehile(), new Laser() );
laserTank.Move();
laserTank.Fire();

var infantrySupport = new Tank( new Car(), new MachineGun() );



Проблема (или достоинство, это еще как посмотреть) такого подхода — отсутствие доступа к приватным членам интегрируемого класса.
Проблема — потому что уменьшаются возможности переиспользования кода
ДОстоинство — потому что уменьшается так же и связность, меньше шансов ошибиться (хотя, конечно, копи-паст тоже не путь к надежному коду )
... << RSDN@Home 1.2.0 alpha 4 rev. 1237>>
Re[6]: [ООП] Хочу странного
От: fmiracle  
Дата: 09.03.10 13:02
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>Здравствуйте, 0x7be, Вы писали:


0>>Мне тут люди возражают, так что не все дело в рынке Просто это традиция такая, если ООП — значит три кита и все такое. Как и любая другая традиция, эта закрепилась просто в силу человеческой природы


VD>Ты плохо знаешь человеческую природу. Человеческое мнение это в 99% случаев то, что ему вдували. Чем дольше вдували, тем крепче мнение.


Так он вобщем-то про то и говорит. Много вдули — закрепилась традиция. И теперь новый ООП-язык без наследования поведения широкая аудитория воспримет как минимум странно.
... << RSDN@Home 1.2.0 alpha 4 rev. 1237>>
Re[3]: [ООП] Хочу странного
От: nikov США http://www.linkedin.com/in/nikov
Дата: 09.03.10 13:09
Оценка: 5 (2)
Здравствуйте, Воронков Василий, Вы писали:

ВВ>Extensions Methods — это синтаксический сахар, *весь* смысл которого заключается в том, что он позволяет вместо


ВВ>
ВВ>MyHelper.DoSomething(foo);
ВВ>


ВВ>писать


ВВ>
ВВ>foo.DoSomething();
ВВ>


Это не совсем так (хотя и не относится к обсуждаемой теме). Попробуй переписать следующий код без extension methods без добавления вспомогательных конструкций:

using System;
using System.Linq;

class C
{
  Func<int> f = "".Count;
}
Re[4]: [ООП] Хочу странного
От: Воронков Василий Россия  
Дата: 09.03.10 13:30
Оценка:
Здравствуйте, nikov, Вы писали:

Честно, не вижу подвоха, а чем проблема? Собственно, берем реализацию, которую показывает рефлектор:

public static int Count<TSource>(this IEnumerable<TSource> source)
{
    if (source == null)
    {
        throw Error.ArgumentNull("source");
    }
    ICollection<TSource> is2 = source as ICollection<TSource>;
    if (is2 != null)
    {
        return is2.Count;
    }
    int num = 0;
    using (IEnumerator<TSource> enumerator = source.GetEnumerator())
    {
        while (enumerator.MoveNext())
        {
            num++;
        }
    }
    return num;
}


Где здесь магия? Все то же самое можно представить в виде обычного метода.
Re[5]: [ООП] Хочу странного
От: nikov США http://www.linkedin.com/in/nikov
Дата: 09.03.10 13:31
Оценка:
Здравствуйте, Воронков Василий, Вы писали:

ВВ>Где здесь магия? Все то же самое можно представить в виде обычного метода.


Но нельзя создать делегат.
Re[6]: [ООП] Хочу странного
От: Воронков Василий Россия  
Дата: 09.03.10 13:37
Оценка:
Здравствуйте, nikov, Вы писали:

ВВ>>Где здесь магия? Все то же самое можно представить в виде обычного метода.

N>Но нельзя создать делегат.

Почему нельзя?


public static Func<Int32> Count<TSource>(this IEnumerable<TSource> source)
        {
            Func<Int32> f = () => {
                    if (source == null)
                    {
                        //throw Error.ArgumentNull("source");
                    }
                    ICollection<TSource> is2 = source as ICollection<TSource>;
                    if (is2 != null)
                    {
                        return is2.Count;
                    }
                    int num = 0;
                    using (IEnumerator<TSource> enumerator = source.GetEnumerator())
                    {
                        while (enumerator.MoveNext())
                        {
                            num++;
                        }
                    }
                    return num;
                };
            return f;
        }


Строка имеет интерфейс IEnumerable<Char>. Через этот интерфейс мы можем делать все что нам хочется — в т.ч. и считать кол-во чаров по условию, например. Какие тут дополнительные возможности дает extension method?
Re[7]: [ООП] Хочу странного
От: nikov США http://www.linkedin.com/in/nikov
Дата: 09.03.10 13:40
Оценка:
Здравствуйте, Воронков Василий, Вы писали:

ВВ> Какие тут дополнительные возможности дает extension method?


Создать делегат типа Func<int> к методу с сигнатурой int Count(IEnumerable<char>) без вспомогательных анонимных функций и явного вызова CreateDelegate.
Re[8]: [ООП] Хочу странного
От: Воронков Василий Россия  
Дата: 09.03.10 14:07
Оценка: -1
Здравствуйте, nikov, Вы писали:

ВВ>> Какие тут дополнительные возможности дает extension method?

N>Создать делегат типа Func<int> к методу с сигнатурой int Count(IEnumerable<char>) без вспомогательных анонимных функций и явного вызова CreateDelegate.

Извини, я снова не понимаю. А что мешает-то?

public static int MyCount<TSource>(IEnumerable<TSource> source)
{
    var is2 = source as ICollection<TSource>;
    
    if (is2 != null)
        return is2.Count;
    
    var num = 0;

    foreach (var c in source)
        num++;

    return num;
}

var f = new Func<IEnumerable<Char>,Int32>(MyCount);


Выглядит это, конечно, менее красиво. Ну так сахар на то и сахар, я совершенно не против extension methods, а очень даже за.
Re[9]: [ООП] Хочу странного
От: nikov США http://www.linkedin.com/in/nikov
Дата: 09.03.10 14:12
Оценка:
Здравствуйте, Воронков Василий, Вы писали:

ВВ>Здравствуйте, nikov, Вы писали:


ВВ>>> Какие тут дополнительные возможности дает extension method?

N>>Создать делегат типа Func<int> к методу с сигнатурой int Count(IEnumerable<char>) без вспомогательных анонимных функций и явного вызова CreateDelegate.

ВВ>Извини, я снова не понимаю. А что мешает-то?


ВВ>
ВВ>var f = new Func<IEnumerable<Char>,Int32>(MyCount);
ВВ>


Ну посмотри внимательно: у тебя делегат типа Func<IEnumerable<Char>,Int32>, то есть он принимает параметр IEnumerable<Char>. А надо создать делегат Func<int> (не принимающий параметров) к тому же методу, передав аргумент при создании делегата.
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.