答:
How DI can be implemented depends very much on the language used.

Here is a simple non-DI example:

class Foo {
    private Bar bar;
    private Qux qux;

    public Foo() {
        bar = new Bar();
        qux = new Qux();
    }
}
```

<p>This sucks, e.g. when for a test I want to use a mock object for <code>bar</code>. So we can make this more flexible and allow instances to be passed via the constructor:</p>

<pre class="lang-java prettyprint-override"><code>class Foo {
    private Bar bar;
    private Qux qux;

    public Foo(Bar bar, Qux qux) {
        this.bar = bar;
        this.qux = qux;
    }
}

// in production:
new Foo(new Bar(), new Qux());
// in test:
new Foo(new BarMock(), new Qux());
</code>```

This already is the most simple form of dependency injection. But this still sucks because everything has to be done manually (also, because the caller can hold a reference to our internal objects and thus invalidate our state).

We can introduce more abstraction by using factories:

One option is for the Foo to be generated by an abstract factory

interface FooFactory {
    public Foo makeFoo();
}

class ProductionFooFactory implements FooFactory {
    public Foo makeFoo() { return new Foo(new Bar(), new Baz()) }
}

class TestFooFactory implements FooFactory {
    public Foo makeFoo() { return new Foo(new BarMock(), new Baz()) }
}

FooFactory fac = ...; // depends on test or production
Foo foo = fac.makeFoo();
```</li>
<li><p>Another option is to pass a factory to the constructor:</p>

<pre class="lang-java prettyprint-override"><code>interface DependencyManager {
    public Bar makeBar();
    public Qux makeQux();
}
class ProductionDM implements DependencyManager {
    public Bar makeBar() { return new Bar() }
    public Qux makeQux() { return new Qux() }
}
class TestDM implements DependencyManager {
    public Bar makeBar() { return new BarMock() }
    public Qux makeQux() { return new Qux() }
}

class Foo {
    private Bar bar;
    private Qux qux;

    public Foo(DependencyManager dm) {
        bar = dm.makeBar();
        qux = dm.makeQux();
    }
}
</code>```

The remaining problems with this are that we need to write a new DependencyManager subclass for each configuration, and that the number of dependencies which can be managed is fairly restricted (each new dependency needs a new method in the interface).

With features like reflection and dynamic class loading we can circumvent this. But this depends very much on the language used. In Perl, classes can be referenced by their name, and I could just do

package Foo {
    use signatures;

    sub new($class, $dm) {
        return bless {
            bar => $dm->{bar}->new,
            qux => $dm->{qux}->new,
        } => $class;
    }
}

my $prod = { bar => 'My::Bar', qux => 'My::Qux' };
my $test = { bar => 'BarMock', qux => 'QuxMock' };
$test->{bar} = 'OtherBarMock';  # change conf at runtime

my $foo = Foo->new(rand > 0.5 ? $prod : $test);
```

<p>In languages like Java, I could have the dependency manager behave similar to a <code>Map<Class, Object></code>:</p>

<pre class="lang-java prettyprint-override"><code>Bar bar = dm.make(Bar.class);
</code>```

To which actual class the Bar.class is resolved can be configured at runtime, e.g. by maintaining an Map<Class, Class> which maps interfaces to implementations.

Map<Class, Class> dependencies = ...;

public <T> T make(Class<T> c) throws ... {
    // plus a lot more error checking...
    return dependencies.get(c).newInstance();
}
```

<p>There is still a manual element involved in writing the constructor. But we can make the constructor completely unnecessary, e.g. by driving the DI via annotations:</p>

<pre class="lang-java prettyprint-override"><code>class Foo {
    @Inject(Bar.class)
    private Bar bar;

    @Inject(Qux.class)
    private Qux qux;

    ...
}

dm.make(Foo.class);  // takes care of initializing "bar" and "qux"
</code>```

Here is an example implementation of a tiny (and very restricted) DI framework: http://ideone.com/b2ubuF, although this implementation is completely unusable for immutable objects (this naive implementation cannot take any parameters for the constructor).

Title: Understanding dependency injection

Body:
I'm reading about dependency injection (DI). To me, it is a very complicated thing to do, as I was reading it was referencing inversion of control (IoC) as well and such I felt I was going to be in for a journey.

This is my understanding: Instead of creating a model in the class which also consumes it, you pass (inject) the model (already filled with interesting properties) to where it is needed (to a new class which could take it as a parameter in the constructor).

To me, this is just passing an argument. I must have miss understood the point? Maybe it becomes more obvious with bigger projects?

My understanding is non-DI (using pseudo code):

```<code>public void Start()
{
    MyClass class = new MyClass();
}

...

public MyClass()
{
    this.MyInterface = new MyInterface();
}
</code>```

And DI would be

```<code>public void Start()
{
    MyInterface myInterface = new MyInterface();
    MyClass class = new MyClass(myInterface);
}

...

public MyClass(MyInterface myInterface)
{
    this.MyInterface = myInterface;
}
</code>```

Could some one shed some light as I'm sure I'm in a muddle here.

Body:
How DI can be implemented depends very much on the language used.

Here is a simple non-DI example:

class Foo {
    private Bar bar;
    private Qux qux;

    public Foo() {
        bar = new Bar();
        qux = new Qux();
    }
}

This sucks, e.g. when for a test I want to use a mock object for bar. So we can make this more flexible and allow instances to be passed via the constructor:

class Foo {
    private Bar bar;
    private Qux qux;

    public Foo(Bar bar, Qux qux) {
        this.bar = bar;
        this.qux = qux;
    }
}

// in production:
new Foo(new Bar(), new Qux());
// in test:
new Foo(new BarMock(), new Qux());

This already is the most simple form of dependency injection. But this still sucks because everything has to be done manually (also, because the caller can hold a reference to our internal objects and thus invalidate our state).

We can introduce more abstraction by using factories:

One option is for the Foo to be generated by an abstract factory

interface FooFactory {
    public Foo makeFoo();
}

class ProductionFooFactory implements FooFactory {
    public Foo makeFoo() { return new Foo(new Bar(), new Baz()) }
}

class TestFooFactory implements FooFactory {
    public Foo makeFoo() { return new Foo(new BarMock(), new Baz()) }
}

FooFactory fac = ...; // depends on test or production
Foo foo = fac.makeFoo();

Another option is to pass a factory to the constructor:

interface DependencyManager {
    public Bar makeBar();
    public Qux makeQux();
}
class ProductionDM implements DependencyManager {
    public Bar makeBar() { return new Bar() }
    public Qux makeQux() { return new Qux() }
}
class TestDM implements DependencyManager {
    public Bar makeBar() { return new BarMock() }
    public Qux makeQux() { return new Qux() }
}

class Foo {
    private Bar bar;
    private Qux qux;

    public Foo(DependencyManager dm) {
        bar = dm.makeBar();
        qux = dm.makeQux();
    }
}

The remaining problems with this are that we need to write a new DependencyManager subclass for each configuration, and that the number of dependencies which can be managed is fairly restricted (each new dependency needs a new method in the interface).

With features like reflection and dynamic class loading we can circumvent this. But this depends very much on the language used. In Perl, classes can be referenced by their name, and I could just do

package Foo {
    use signatures;

    sub new($class, $dm) {
        return bless {
            bar => $dm->{bar}->new,
            qux => $dm->{qux}->new,
        } => $class;
    }
}

my $prod = { bar => 'My::Bar', qux => 'My::Qux' };
my $test = { bar => 'BarMock', qux => 'QuxMock' };
$test->{bar} = 'OtherBarMock';  # change conf at runtime

my $foo = Foo->new(rand > 0.5 ? $prod : $test);

In languages like Java, I could have the dependency manager behave similar to a Map<Class, Object>:

Bar bar = dm.make(Bar.class);

To which actual class the Bar.class is resolved can be configured at runtime, e.g. by maintaining an Map<Class, Class> which maps interfaces to implementations.

Map<Class, Class> dependencies = ...;

public <T> T make(Class<T> c) throws ... {
    // plus a lot more error checking...
    return dependencies.get(c).newInstance();
}

There is still a manual element involved in writing the constructor. But we can make the constructor completely unnecessary, e.g. by driving the DI via annotations:

class Foo {
    @Inject(Bar.class)
    private Bar bar;

    @Inject(Qux.class)
    private Qux qux;

    ...
}

dm.make(Foo.class);  // takes care of initializing "bar" and "qux"

Here is an example implementation of a tiny (and very restricted) DI framework: http://ideone.com/b2ubuF, although this implementation is completely unusable for immutable objects (this naive implementation cannot take any parameters for the constructor).


问:
Single Responsibility Principle and higher levels of abstraction
Two common phrasings for the Single Responsibility Principle (SRP) are "each module should be responsible for a single feature or functionality in a system", and "each module should have only one reason to change".

My questions is: is this something that we should absolutely strive for in every class of a system, or should it be relaxed when we combine lower-level modules to compose the more abstract modules?

At the extreme case, the top-level module in a system will be responsible for the entire gamut of system functions, so it looks like it may not be possible to respect the SRP in this kind of module.

答:
If the top-level module delegates all of its functionality to submodules and only glues them together, that leaves it with one responsibility ("gluing the other modules together") and one reason to change ("something fundamental changed about the architecture that requires a change in the submodule set"). Every other change to the program should not cause a change to the top-level module, just the appropriate submodules.

The SRP is an ideal. Like all ideals, you have to weigh the cost of pursuing it against the benefits it brings.

ContentLicense: CC BY-SA 3.0


问:
Is it possible to have setup and tear down methods run only for specific unittests?
I currently have a test class with a setUp method for creating a temp file and a tearDown method for deleting a temp file.

However, only some of the the test_ methods in that class require this functionality.

Is possible to either ignore those 2 methods for the test cases which do not require it or to only call those 2 methods for test cases which do require it?

It feels a bit 'wrong' to call these 2 methods for every test even if the temp file is not getting used in each one.

答:
Just put those specific tests into a new TestCase class:

```<code>class TestsWithTemporaryFile(TestCase):
    def setUp(self):
         # set up temporary file

    def tearDown(self):
         # clean up temporary file

    def test_foo(self):
         # ...

    def test_bar(self):
         # ...

class TestsWithoutTemporaryFile(TestCase):
    def test_spam(self):
         # ...

    def test_eggs(self):
         # ...
</code>```

The test runner will find both test cases; nothing says you need to put all your tests into one TestCase.

Body:
Just put those specific tests into a new TestCase class:

class TestsWithTemporaryFile(TestCase):
    def setUp(self):
         # set up temporary file

    def tearDown(self):
         # clean up temporary file

    def test_foo(self):
         # ...

    def test_bar(self):
         # ...

class TestsWithoutTemporaryFile(TestCase):
    def test_spam(self):
         # ...

    def test_eggs(self):
         # ...

The test runner will find both test cases; nothing says you need to put all your tests into one TestCase.


答:
It feels a bit 'wrong' to call these 2 methods for every test even if the temp file is not getting used in each one.

So the code will be simpler when you let the temp file beeing created and deleted in all cases? And I guess the performance hit is negligible? Then what you are trying is just a form of premature optimization. Don't do this (at least, not as long the performance differerence has no reasonable impact on your workflow).

Title: Is it possible to have setup and tear down methods run only for specific unittests?

Body:
I currently have a test class with a setUp method for creating a temp file and a tearDown method for deleting a temp file.

However, only some of the the test_ methods in that class require this functionality.

Is possible to either ignore those 2 methods for the test cases which do not require it or to only call those 2 methods for test cases which do require it?

It feels a bit 'wrong' to call these 2 methods for every test even if the temp file is not getting used in each one.

ContentLicense: CC BY-SA 4.0


问:
Regarding interfaces of classes in OOP
When one says "a class' interface":

Does he/she refer to all of the get and set methods - or do they refer only to the methods' signatures and return types, without the inner implementation of these methods? (Aka, the implementation of a 'get' method isn't considered part of the interface, but rather part of the inner implementation of the class. The interface is the return type for that method and the signature of that method).

答:
The interface to a class is essentially what is visible to other classes using it.

The interface to a class would therefore be the declarations of all the public methods and variables it exposes.  It wouldn't include the implementation details of each method.

Where a class has protected (or package private for Java) methods and variables, then they should also be considered part of the interface, since they can also be accessed by other classes, albeit with some restrictions.

Title: Regarding interfaces of classes in OOP


问:
Which classes should be autowired by Spring (when to use dependency injection)?
I have been using Dependency Injection in Spring for some time now, and I understand how it works and what are some pros and cons of using it. However, when I'm creating a new class I often wonder - Should this class be managed by Spring IOC Container?

And I don't want to talk about differences between @Autowired annotation, XML configuration, setter injection, constructor injection, etc. My question is a general one.

Let's say we have a Service with a Converter:

```<code>@Service
public class Service {

    @Autowired
    private Repository repository;

    @Autowired
    private Converter converter;

    public List<CarDto> getAllCars() {
        List<Car> cars = repository.findAll();
        return converter.mapToDto(cars);
    }
}

@Component
public class Converter {

    public CarDto mapToDto(List<Car> cars) {
        return new ArrayList<CarDto>(); // do the mapping here
    }
}
</code>```

Clearly, the converter doesn't have any dependencies, so it's not necessary for it to be autowired. But for me it seems better as autowired. Code is cleaner and easy to test. If I write this code without DI, the service will look like that:

```<code>@Service
public class Service {

    @Autowired
    private Repository repository;

    public List<CarDto> getAllCars() {
        List<Car> cars = repository.findAll();
        Converter converter = new Converter();
        return converter.mapToDto(cars);
    }
}
</code>```

Now it's much more difficult to test it. Moreover, new converter will be created for every convert operation, even though it's always in the same state, which seems like an overhead.

There are some well known patterns in Spring MVC: Controllers using Services and Services using Repositories. Then, if Repository is autowired (which it usually is), then Service has to be autowired too. And this is quite clear. But when do we use @Component annotation? If you have some static util classes (like converters, mappers) - do you autowire them?

Do you try to make all classes autowired? Then all the class dependencies are easy to inject (once again, easy to understand and easy to test). Or do you try to autowire only when it's absolutely necessary?

I've spent some time looking for some general rules on when to use autowiring, but I couldn't find any specific tips. Usually, people talk about "do you use DI? (yes/no)" or "what type of dependency injection do you prefer", which doesn't answer my question.

I would be grateful for any tips concerning this topic!

答: We can separate the classes on the basis of the function of that class such that controllers, service, repository,entity. We may use other classes for our logic only not for the purpose of controllers,service etc.,on that occasion we could annotate that classes with @component. This will automatically register that class in the spring container. If it is registered then it will be managed by spring container. Concept of dependency injection and inversion of control can be supplied to that annotated class.</p>


问:
Understanding dependency injection
I'm reading about dependency injection (DI). To me, it is a very complicated thing to do, as I was reading it was referencing inversion of control (IoC) as well and such I felt I was going to be in for a journey.

This is my understanding: Instead of creating a model in the class which also consumes it, you pass (inject) the model (already filled with interesting properties) to where it is needed (to a new class which could take it as a parameter in the constructor).

To me, this is just passing an argument. I must have miss understood the point? Maybe it becomes more obvious with bigger projects?

My understanding is non-DI (using pseudo code):

```<code>public void Start()
{
    MyClass class = new MyClass();
}

...

public MyClass()
{
    this.MyInterface = new MyInterface();
}
</code>```

And DI would be

```<code>public void Start()
{
    MyInterface myInterface = new MyInterface();
    MyClass class = new MyClass(myInterface);
}

...

public MyClass(MyInterface myInterface)
{
    this.MyInterface = myInterface;
}
</code>```

Could some one shed some light as I'm sure I'm in a muddle here.

答: If you pass in an abstract reference type then the calling code can pass in any object that extends/implements the abstract type. So in future the class that uses the object could use a new object that has been created without ever modifying its code.</p>

Title: Understanding dependency injection


问:
Can the author of code licensed under CC-NC-ND use it in commercial closed-source software?
I am working on project on which I need to open-source part of my code in order to simplify extension by the enduser.

What I want, is to make an npm module, that will expose part of my code, so my users can build extensions for the product (in JavaScript), but I want a guarantee that this code will not be used for commercial or other development work, beside extensions for my product.

I found Creative Commons Attribution NonCommercial NoDerivs license to be a fit.

My problem: Can I, as the author of this code, use it in a commercial closed-source application?

Disclaimer: I know this is kind of a legal question, but please, state what you think, no one is holding you accountable/liable for it. Thanks.

答:
Copyright licenses only specify what others can do with your code. If you are the copyright holder of the code, then you have all the rights to do with that code as you like and that includes using the code in ways that is not permitted for others.

You are the copyright holder if you wrote the code yourself and it was not written as part of your job or under contract.

Regarding your choice of license: Using Creative Commons licenses for software is not recommended.


答:
Can I, as the author of this code, use it in a commercial closed-source application?

(Well the author and the copyright holder are not necessarily the same thing.  An author may not own the copyright in the first place (e.g. employees writing code), or he / she / they may assign the copyright to someone else.)

So:

If you are the current copyright holder - Yes.  See below.

If you are working for the copyright holder - Ask the boss.

If you have assigned the copyright to someone else - It depends ...

The license forbids this, because what you are doing is commercial use.

However, it is common practice to include a "license back" in copyright assignment agreements.  So check to see if that applies, and what right are being granted by that route.

Copyright-based license are actually a grant of limited rights by the copyright holder to others.  If you are the copyright holder, you don't need to grant yourself rights that you already have.

IANAL ... obviously.

Title: Can the author of code licensed under CC-NC-ND use it in commercial closed-source software?

Body:
I am working on project on which I need to open-source part of my code in order to simplify extension by the enduser.

What I want, is to make an npm module, that will expose part of my code, so my users can build extensions for the product (in JavaScript), but I want a guarantee that this code will not be used for commercial or other development work, beside extensions for my product.

I found Creative Commons Attribution NonCommercial NoDerivs license to be a fit.

My problem: Can I, as the author of this code, use it in a commercial closed-source application?

Disclaimer: I know this is kind of a legal question, but please, state what you think, no one is holding you accountable/liable for it. Thanks.


答:
Our friends on Stack Overflow have a nice answer to this. My favourite is the second answer, including the quote:

"Dependency Injection" is a 25-dollar term for a 5-cent concept. (...) Dependency injection means giving an object its instance variables. (...).

from James Shore's blog. Of course, there are more complex versions / patterns layered on top of this, but it is enough to basically understand what is going on. Instead of an object creating its own instance variables, they are passed in from outside.

Title: Understanding dependency injection


问:
Set distances algorithm question
I have multiple sets containing integers. An integer maybe present in one set or multiple sets. I would like to find/match the sets with the most common integers.

Example
s1 {1, 2, 3, 4}
s2 {1, 3, 4, 5}
s3 {6, 7, 8, 9}
s4 {1, 6, 8, 10}

In this case, I would like to "efficiently" group s1+s2 as they have the most overlapping elements (3) followed by s3+s4(2) s1+s4(1).

You can do this the brute force way (match all possibilities - then sort)
Looking for an efficient way to do this.

答:
I'm assuming that all of your sets are of the same size (i.e. the same number of elements)

For ordered sets you sort on the first element O(nlog(n)), then start partitioning into equivalence classes.

Sort on the first element O(nlog(n))

Group the sets into classes by equivalence of the first element O(k)

In each class repeat the above two steps on the second element, the third element, etc.

For a given set size, this will be O(nlog(n)) overall, for n the number of sets.  It is not O(mlog(m)) for m, the number of set elements (size of the sets).

This is similar to a Voronoi diagram on a special metric.

I just noticed that you assume unordered sets, this answer from theoretical CS has a good hash based solution, there can still be hash collisions, but you can reduce them as much as you want, to within the machine precision of the computer...

Title: Set distances algorithm question


答:
I did something similar a few years ago.  In my case we had tens of thousands of sets, and each set had around a dozen integers.  Not all sets had the same number of integers. Since these are "sets", I'm assuming the order of the integers in each set is irrelevant.

In our case, step 1 was to compute a hash of the numbers of each set.  We'd then sort the list of hashes and pull out the duplicates.

Step 2 was to compute the hash of each set less one element, then do the same.  For example,

s1 { 1,2,3,4 } would yield 4 hashes (2,3,4) and (1,3,4) and (1,2,4) and (1,2,3).

We'd make a new list associating all 4 hashes with s1 and sort/look for duplicates.  This would find the (1,3,4) match between s1 and s2.

We'd do a similar step 3 (omitting 2 from each set) and so on.  It took some experimentation to figure out where the cost/benefit cutoff was.  This is definitely an expensive brute force approach, but it worked well for us.

Title: Set distances algorithm question

Body:
I have multiple sets containing integers. An integer maybe present in one set or multiple sets. I would like to find/match the sets with the most common integers.

Example
s1 {1, 2, 3, 4}
s2 {1, 3, 4, 5}
s3 {6, 7, 8, 9}
s4 {1, 6, 8, 10}

In this case, I would like to "efficiently" group s1+s2 as they have the most overlapping elements (3) followed by s3+s4(2) s1+s4(1).

You can do this the brute force way (match all possibilities - then sort)
Looking for an efficient way to do this.


问:
Should utility base classes be avoided
Knowing that C# doesn't support multiple inheritance, is it considered bad form to write a utility base class?

Some initial thoughts:

I could create an interface and a concretion, but then the implementation isn't portable

Should the developer need to extend the class in say, a decorator pattern, they could implement this new class and inherit the base class in their new class

EDIT:

N.B. I'm not talking about vanilla inheritance here e.g. poodle<--dog<--mammal<--animal

More this sort of thing (lifted from here):

```<code>    using log4net;
    using log4net.Config;

    public class LogTest2
    {
        private static readonly ILog logger =
              LogManager.GetLogger(typeof(LogTest2));

    static LogTest2()
    {
        DOMConfigurator.Configure();
    }

    static void Main(string[] args)
    {
        logger.Debug("Here is a debug log.");
        logger.Info("... and an Info log.");
        logger.Warn("... and a warning.");
        logger.Error("... and an error.");
        logger.Fatal("... and a fatal error.");
    }
}
</code>```

If I were to drop this into say, a WCF service, it would be expedient for the private member variable, constructor and perhaps some wrapper methods to sit in a base class to save cluttering up the service code (and make it reusable).

So far, so dull.

However:

What if I wanted to add some other sort of logging not supported by log4net? E.g. Acme Corp provide some class to iMessage the support team if an issue occurs.

Base class

Had I implemented the log4net stuff in a base class, I'd then have to create some new master base class that supports both classes and inherit this.

Interface

I could implement an interface but the concretion would still be in the service code which we're trying to avoid. Acme Corp's class can of course now drop straight in but we're implementing two sets of code which do very similar things in different ways.

答: I would recommend the interface and the concretion. The implementation can still be portable through the use of delegation, ie. another class implementing the interface can get a hold of an instance of the concrete version and delegate to it when it needs to use the concrete functionality. This provides a greater flexibility if you really expect implementing/sub-classes to need to inherit from multiple other sources.</p>

Title: Should utility base classes be avoided


答:
I could create an interface and a concretion, but then the implementation isn't portable

There's a design trade-off between using a sealed class (or a class with a finite number of subclasses) and interfaces. With a sealed class, you have the same implementation everywhere in the program. With an interface, you gain the flexibility of having alternative implementations, but you have to hope every implementation is correct; a particular part of the program could be using Implementation A which is correct, while another part may rely on the same interface but be using buggy Implementation B.

So, no, having a dependency on a concrete class isn't inherently a bad thing.

(As for unsealed classes, these behave similarly to interfaces in that you have to trust that all subclasses are correct, but are not as flexible as interfaces and run the risk of the Fragile Base Class Problem.)

Should the developer need to extend the class in say, a decorator pattern, they could implement this new class and inherit the base class in their new class

If you need this kind of extensibility, then use an interface. You should forbid inheritance unless you design your class for it (and you probably don't want to if you can avoid it at all, because composition is, well, more composable.)

Title: Should utility base classes be avoided

Body:
Knowing that C# doesn't support multiple inheritance, is it considered bad form to write a utility base class?

Some initial thoughts:

I could create an interface and a concretion, but then the implementation isn't portable

Should the developer need to extend the class in say, a decorator pattern, they could implement this new class and inherit the base class in their new class

EDIT:

N.B. I'm not talking about vanilla inheritance here e.g. poodle<--dog<--mammal<--animal

More this sort of thing (lifted from here):

```<code>    using log4net;
    using log4net.Config;

    public class LogTest2
    {
        private static readonly ILog logger =
              LogManager.GetLogger(typeof(LogTest2));

    static LogTest2()
    {
        DOMConfigurator.Configure();
    }

    static void Main(string[] args)
    {
        logger.Debug("Here is a debug log.");
        logger.Info("... and an Info log.");
        logger.Warn("... and a warning.");
        logger.Error("... and an error.");
        logger.Fatal("... and a fatal error.");
    }
}
</code>```

If I were to drop this into say, a WCF service, it would be expedient for the private member variable, constructor and perhaps some wrapper methods to sit in a base class to save cluttering up the service code (and make it reusable).

So far, so dull.

However:

What if I wanted to add some other sort of logging not supported by log4net? E.g. Acme Corp provide some class to iMessage the support team if an issue occurs.

Base class

Had I implemented the log4net stuff in a base class, I'd then have to create some new master base class that supports both classes and inherit this.

Interface

I could implement an interface but the concretion would still be in the service code which we're trying to avoid. Acme Corp's class can of course now drop straight in but we're implementing two sets of code which do very similar things in different ways.


答:
Bart and Stephan's answers are correct: YES, as the copyright holder, you can do whatever you want with it.

ADDITIONALLY:

You're looking for a license "to simplify extension by the enduser." Insomuchas you're making a module that exposes some of your code for them to manipulate.

Are you sure you don't simply need to make an API for them to interface? They receive none of your code, just some documentation about how to interface with it.

If you expect the end-users to change and update this module, then yes, an open-source license is a good idea. But this CC-NC-ND license is not a good idea because of the ND portion. No derivatives means that they cannot change or update the module, which is why you're open-sourcing it in the first place.

This CC-NC-ND license is more for artists rather than coders. They can look at the code, but can't touch it. If you want end-users to contribute code to your project, go with another open source license.


问:
How to check robustness in a service that includes multiple points of failure in workflow, including FTP
As part of my workflow, I need to do all these steps in one transaction
- I need to ftp files to 2 different FTP servers.
- There is also a spreadsheet that gets generated which needs to be FTP'ed. Can this be streamed, instead of downloading and then pushed to FTP server.

I am using Ruby Net::SFTP and Net::FTP libraries to send the files.

I would like it to be robust. I am not sure if I need to do anything else or of this is good enough.

Just to be clear, this is already working in production, I am not stuck, just looking to exchange design/architecture ideas on how to improve this.

答:
It depends what you mean by "robust" e.g. considering scenarios like:

PUT fails on remote host

PUT succeeds but file is corrupted somehow

Host is temporarily unavailable

Host is permanently unavailable (e.g. wrong config, or host is decommissioned)

You can code around this (or buy software that provides guarantees around delivery), but if you're in control of the whole workflow, it may be better to have clients "pull" the files rather than having the publishers "push" them. The system I work on creates and sends a huge amount of files, and we have no idea if the remote clients even need some of them. A "pull" model at least tells you that a system somewhere is actively trying to fetch a given file.

You could, for example, built a service that accepts file requests, and builds them if they are not available, or else uses an existing / cached version, perhaps from the filesystem. A REST API would be a natural fit for this, e.g.

http://server.example.com/myservice/mydata/file12345.csv

...would build file12345.csv on-demand and cache it for subsequent requests (if you needed that).


答:
Ahh, with FTP, the simple answer is - you don't.

What you can do is to retrieve the file you sent to the FTP server, and check it is the same as the original file. If they match, all worked as well as you'd hoped.

This gets tricky if you're not allowed to read from the FTP server (as some credit card acquirers do), security is set up such that you're allowed to write to some directories but not read from them. In these cases, the server tends to have a service that generates a summary report of your upload that you can retrieve from a read-only directory. In the case of acquirers that do not do this, you just have to cross your fingers and wait for them to complain usually on the following day.

Title: How to check robustness in a service that includes multiple points of failure in workflow, including FTP

Body:
As part of my workflow, I need to do all these steps in one transaction
- I need to ftp files to 2 different FTP servers.
- There is also a spreadsheet that gets generated which needs to be FTP'ed. Can this be streamed, instead of downloading and then pushed to FTP server.

I am using Ruby Net::SFTP and Net::FTP libraries to send the files.

I would like it to be robust. I am not sure if I need to do anything else or of this is good enough.

Just to be clear, this is already working in production, I am not stuck, just looking to exchange design/architecture ideas on how to improve this.


问:
Why do some projects have getters and setters for public instance variables?
I was looking into an open-source game framework project written in Java. It has several classes that:

Have public instance variables.

Have getter/setters for such variables.

Generally, I write getters/setters when I want to encapsulate some behavior that occurs when a property is modified.

However, looking at the code, it literally goes something like this:

```<code>public class Test {
    public int value;
    public void setValue(x) {
        value = x;
    }
    public void getValue() {
        return value;
    }
}
</code>```

Then I thought about checking out the rest of the framework and see how do they modify such value, which may give me a hint on why did they do the above.

From what I've seen, they do it like this:

```<code>object.value = 100;
</code>```

Without using the getters/setters.

So now I'm not sure what was the point of creating getters/setters.

So, my question is, is there a reason I would want to create getters/setters for a public value, if such getters/setters don't even implement any kind of special behaviour?

答:
In a number of languages, classes can expose fields, but interfaces cannot.  In some cases, it may be useful to a class expose information via both its class type (in which case consumers could uses fields) and via an interface (in which case consumers must use methods).

For example, a Location3d interface might define methods getX(), getY(), and getZ().  A Point3d class might define fields X, Y, Z and also implement that interface.  Other objects which have locations, but don't store the X, Y, and Z directly, might implement the interface to allow other entities to inquire about their position.

Continuing the example, a Monster class in a game might expose an EnemyLocation which holds a reference back to the monster, and implements getX() etc. methods so they will continuously report the location of the monster's current enemy.  If the EnemyLocation stored coordinates directly, or even if it held a reference to the current enemy's Point3d, the coordinates wouldn't get updated when a monster finds a new enemy to target.  If, however, its getX() etc. methods examine the attached monster, and read the present location of that monster's present enemy, they can always report up-to-date data.


问:
What file extension do you use for your template/view files in PHP?
I'm building a Model-View-Controller framework, and it has come time to decide how I will be creating and using view templates and layouts.

Some frameworks use special extensions for these files.  CakePHP uses .ctp.

I have heard-of/seen .tpl files, though I've never used them myself.

There is the .inc extension, which doesn't feel right, and of course, I could stick with plaon ol' .php.

For that matter why not .awesome?

What do you use for your template files?  Is there any benefit to using a special file extension for these files?  Are you partial to a certain extension for nostalgia or convention alone?  They're typically (and will be in my project) already in their own directory, so I assume there must be some reason they are differentiated by their extension in projects like CakePHP.

答:
For Smarty templates, the standard is .tpl.

For Twig templates, the standard is .twig.

For Latte templates, the standard is .latte.

For Mustache templates, the standard is .mustache.

For CakePHP templates, the standard is .ctp.

If you create your own templating engine, it's best to avoid any of these five standards to avoid confusion. Any other extension that isn't already commonly associated with another filetype would do fine. Either that, or you could just go for .html / .xml if your templates are valid .html / .xml.

Whichever extension you pick and whichever template type you pick, it's always best to go for an extension that's recognised by your IDE. If you don't, auto-formatting and code highlighting features of your IDE have to be set manually or can't be set at all, which makes your template system less user friendly.

ContentLicense: CC BY-SA 2.5


问:
Should PHP view files be called something other than '.php'?
By default, any file that PHP touches is usually suffixed with .php. It's universally understood by Apache / Nginx as the default for PHP files and most setups expect PHP files to end in this extension. In short, .php is the standard for everything PHP.

However, I'm wondering if perhaps view files should have a different extension to help differentiate them from other PHP files.

First, when it comes to views I have found that almost all MVC frameworks using a matching view file named after the controller or method. In addition, you generally also have a matching model named the same thing. This causes a problem with most IDE's and editors.

For example, you might have a "user" controller, a "user" view, and a "user" model. The results in having three files open called "user.php" which makes it a bother when you are moving around and clicking on the wrong tabs.

Second, separating views as a fundamentally different kind of PHP file (the presentation type) is another argument for changing the extension of the view files to something other than .php. Something that immediately tells your brain what type of content belongs in it.

Third, some applications expose parts (or all) of the PHP files in the webroot and it's directories. Rather than adding something like <?php if(!defined(ABC)) die('not allowed'); it would be nice to have an easy way to forbid access to views while allowing other files like the customary index.php.

Are there any other good/bad reasons to think it's a good idea to change the file extension of view files?

答:
It really depends on the content of your view files.

A view could look like this :

```<code><?php

class Home_View {

    public function render($parameters) {
        [...]
    }

    [...]
}

?>
</code>```

It could also look like this :

```<code><html>
    <head>
        <?php echo $parameters['styles'] ?>
    <title><?php echo $parameters['title'] ?></title>
    </head>
    <body>
        <?php echo $parameters['content'] ?>
    </body>
</html>
</code>```

Both of the above cases, it makes sense to use the .php extension, because your view is basicly just plain PHP.

A view doesn't have to be plain PHP, though. A view could one of many other filetypes that can be understood by your controller.

If your view is a valid Smarty template, consider .tpl.

If your view is a valid Twig template, consider .twig.

If your view is a valid Latte template, consider .latte.

If your view is a valid Mustache template, consider .mustache.

If your view is valid HTML, consider .phtml or .html.

If your view is a valid Atom file, consider .atom.

If your view is a valid JSON file, consider .json.

If your view is a valid XML file, consider .xml.

You could of course always used your own custom extension, but I wouldn't recommend it because you'd not be able to take advantage of the autoformatting and code highlighting features of your favorite IDE (at least not out of the box).

Body:
It really depends on the content of your view files.

A view could look like this :

<?php

class Home_View {

    public function render($parameters) {
        [...]
    }

    [...]
}

?>

It could also look like this :

<html>
    <head>
        <?php echo $parameters['styles'] ?>
    <title><?php echo $parameters['title'] ?></title>
    </head>
    <body>
        <?php echo $parameters['content'] ?>
    </body>
</html>

Both of the above cases, it makes sense to use the .php extension, because your view is basicly just plain PHP.

A view doesn't have to be plain PHP, though. A view could one of many other filetypes that can be understood by your controller.

If your view is a valid Smarty template, consider .tpl.

If your view is a valid Twig template, consider .twig.

If your view is a valid Latte template, consider .latte.

If your view is a valid Mustache template, consider .mustache.

If your view is valid HTML, consider .phtml or .html.

If your view is a valid Atom file, consider .atom.

If your view is a valid JSON file, consider .json.

If your view is a valid XML file, consider .xml.

You could of course always used your own custom extension, but I wouldn't recommend it because you'd not be able to take advantage of the autoformatting and code highlighting features of your favorite IDE (at least not out of the box).


问:
What negative consequences can arise from this language design rule?
Clarification: the rule is meant to prevent accessing variables that are not declared yet.

Clarification 2: the rule mandates that the compiler follows calls to functions which are defined in the same scope as the call and happen before the actual definition (forward referencing)  - making the compiler much alike an interpreter.

I'm thinking about a fictional programming language that behaves similar to JavaScript when declaring functions: that is, when using the function keyword to create named functions, they get "hoisted" to the top of the scope and can be used anywhere where their name is visible.

For example, the following is legal:

```<code>f();
function f() { console.log("f called") };
</code>```

However, there is a potential problem: what if the function f uses a variable x, that is defined after the call, like here:

```<code>f();
var x = 1;
function f() { console.log(x); }
</code>```

In case of JavaScript, this is also legal, because variables are hoisted as well - the program gets essentially transformed into something like this:

```<code>var x;
function f() { console.log(x); }

f();
x = 1;
</code>```

And therefore just prints undefined.

In my fictional language, variables wouldn't get hoisted, which means that the example before would produce an error. The rule concerns how this error is generated:

Functions are visible for the entire block in which they are defined,
  but it is illegal to call a function that accesses a variable declared
  after the call.

This means that each time the compiler for this language would encounter a function call, it would have to check if the function is defined in the current scope, and if it is, check if it accesses variables in the current scope that are declared after the call.

The reason for this rule is that it makes no sense to access variables before they are declared. Hoisting the variables to the top of their scopes like JavaScript does is a hack that only leaves room for error! This is why I believe it must not be done, but such situations should be detected and treated as errors (because they are, you're referencing something that doesn't chronologically exist yet).

I'm looking for reasons why this is a bad rule, i.e. results in complications or inconsistencies.

The reason I suspect that the rule is a bad one is that it does not exist in the Scala language. Scala solved this problem with a much more general rule:

The scope of a name introduced by a declaration or definition is the
  whole statement sequence containing the binding. However, there is a
  restriction on forward references in blocks: In a statement sequence
  s[1]...s[n] making up a block, if a simple name in s[i] refers to
  an entity defined by s[j] where j >= i, then for all s[k]
  between and including s[i] and s[j],

s[k] cannot be a variable definition.

If s[k] is a value definition, it must be lazy.

UPDATE:

For the time being I have adopted Scala's approach.

This approach is a more general version of my rule: it will catch all illegal accesses, but also some that are not - this is a tradeoff that I'm willing to make since I think that my rule may be too complicated or even impossible to implement.

Here's the rephrased/explained rule from Scala:

Variables cannot be forward-referenced, but lazy values, functions defined with def (which are just syntax sugar for lambdas assigned to (lazy) values, might even remove them as Doval suggested), classes, and modules can.

The restriction is that between the reference and the declaration (inclusive), there must be no variable definitions, because they might be altered by the entity being referenced before they are introduced to the program.

答:
You've already created at least one inconsistency, and a particularly damning one at that - treating functions differently from other values. A function declaration is conceptually the same as binding a variable to an anonymous function, but you're asserting that "regular" variables don't get hoisted while function declarations do. So...

```<code>f()
function f() { /* ... */ }
</code>```

Works, but...

```<code>f()
var f = function() { /* ... */ } // Pretend this is anonymous function syntax
</code>```

Doesn't. (And if you don't allow passing functions around like any other value, your language is horribly crippled.) Next, what happens if a function is redefined?

```<code>f()
function f() { /* definition 1 */ }
...
function f() { /* definition 2 */ }
</code>```

If you treat this as an error, you're once again rejecting functions as values. There's no reason you shouldn't be able to do:

```<code>var f = function() { /* def 1 */ }
f = function() { /* def 2 */ }
</code>```

So let's assume you'll allow the function to be redefined. How do you deal with lexical scoping?

```<code>function f() { /* definition 1 */ }
function bar() {
    f()
    function f() { /* definition 2 */ }
</code>```

If you hoist definition 2 to the top of bar's scope, you end up with this:

```<code>function f() { /* definition 1 */ }
function bar() {
    function f() { /* definition 2 */ }
    f()
</code>```

Which means you can never call the outer definition from a nested scope unless you give the inner function a different name. Moreover, in any other language, the meaning of the above program is independent of the choice of name for definition 2. The hoisting rule changes the meaning depending on whether there's a name collision or not. On the other hand if you don't hoist definition 2 to the top of bar, you've broken your own rule.

Body:
You've already created at least one inconsistency, and a particularly damning one at that - treating functions differently from other values. A function declaration is conceptually the same as binding a variable to an anonymous function, but you're asserting that "regular" variables don't get hoisted while function declarations do. So...

f()
function f() { /* ... */ }

Works, but...

f()
var f = function() { /* ... */ } // Pretend this is anonymous function syntax

Doesn't. (And if you don't allow passing functions around like any other value, your language is horribly crippled.) Next, what happens if a function is redefined?

f()
function f() { /* definition 1 */ }
...
function f() { /* definition 2 */ }

If you treat this as an error, you're once again rejecting functions as values. There's no reason you shouldn't be able to do:

var f = function() { /* def 1 */ }
f = function() { /* def 2 */ }

So let's assume you'll allow the function to be redefined. How do you deal with lexical scoping?

function f() { /* definition 1 */ }
function bar() {
    f()
    function f() { /* definition 2 */ }

If you hoist definition 2 to the top of bar's scope, you end up with this:

function f() { /* definition 1 */ }
function bar() {
    function f() { /* definition 2 */ }
    f()

Which means you can never call the outer definition from a nested scope unless you give the inner function a different name. Moreover, in any other language, the meaning of the above program is independent of the choice of name for definition 2. The hoisting rule changes the meaning depending on whether there's a name collision or not. On the other hand if you don't hoist definition 2 to the top of bar, you've broken your own rule.


答:
Dependency injection is just passing a parameter, but that still leads to some issues, and the name is intended to focus a bit on why the difference between creating an object vs. passing one in is important.

It's important because (pretty obviously) any time object A calls type B, A is dependent on how B works.  Which means that if A makes the decision of specifically which concrete type of B it will use, then a lot of flexibility in how A can be used by outside classes, without modifying A, has been lost.

I mention this because you talk about "missing the point" of dependency injection, and this is much of the point of why people like to do it.  It may just mean passing a parameter, but whether you do so can be important.

Also, some of the difficulty in actually implementing DI does show up better in large projects.  You will generally move the actual decision of which concrete classes to use all the way out to the top, so your start method might look like:

```<code>public void Start()
{
    MySubSubInterfaceA mySubSubInterfaceA = new mySubSubInterfaceA();
    MySubSubInterfaceB mySubSubInterfaceB = new mySubSubInterfaceB();
    MySubInterface mySubInterface = new MySubInterface(mySubSubInterfaceA,mySubSubInterfaceB);
    MyInterface myInterface = new MyInterface(MySubInterface);
    MyClass class = new MyClass(myInterface);
}
</code>```

but with another 400 lines of this kind of riveting code.  If you imagine maintaining that over time the appeal of DI containers becomes more apparent.

Also, imagine a class that, say, implements IDisposable.  If the classes that use it get it via injection rather than creating it themselves, how do they know when to call Dispose()?  (Which is another issue that a DI container deals with.)

So, sure, dependency injection is just passing a parameter, but really when people say dependency injection they mean "passing a parameter to your object vs. the alternative of having your object instantiate something itself", and dealing with all the benefits of drawbacks of such an approach, possibly with the help of a DI container.

Title: Understanding dependency injection

Body:
Dependency injection is just passing a parameter, but that still leads to some issues, and the name is intended to focus a bit on why the difference between creating an object vs. passing one in is important.

It's important because (pretty obviously) any time object A calls type B, A is dependent on how B works.  Which means that if A makes the decision of specifically which concrete type of B it will use, then a lot of flexibility in how A can be used by outside classes, without modifying A, has been lost.

I mention this because you talk about "missing the point" of dependency injection, and this is much of the point of why people like to do it.  It may just mean passing a parameter, but whether you do so can be important.

Also, some of the difficulty in actually implementing DI does show up better in large projects.  You will generally move the actual decision of which concrete classes to use all the way out to the top, so your start method might look like:

public void Start()
{
    MySubSubInterfaceA mySubSubInterfaceA = new mySubSubInterfaceA();
    MySubSubInterfaceB mySubSubInterfaceB = new mySubSubInterfaceB();
    MySubInterface mySubInterface = new MySubInterface(mySubSubInterfaceA,mySubSubInterfaceB);
    MyInterface myInterface = new MyInterface(MySubInterface);
    MyClass class = new MyClass(myInterface);
}

but with another 400 lines of this kind of riveting code.  If you imagine maintaining that over time the appeal of DI containers becomes more apparent.

Also, imagine a class that, say, implements IDisposable.  If the classes that use it get it via injection rather than creating it themselves, how do they know when to call Dispose()?  (Which is another issue that a DI container deals with.)

So, sure, dependency injection is just passing a parameter, but really when people say dependency injection they mean "passing a parameter to your object vs. the alternative of having your object instantiate something itself", and dealing with all the benefits of drawbacks of such an approach, possibly with the help of a DI container.


问:
How to prevent the vicious circle of testing via customer
I recently asked this question and this comment and made me ponder the whole process of releasing an update to the customers. The next update for our software is planned and the previous time it went horribly wrong because of regression, bad testing, etc...

This time we want to prevent the scenario that we test via our customer and made some unit tests and other minor improvements.
However, there is not enough time to make unit tests for all the features that lack unit tests or the features that need to be build yet.
So the answer for this question 'Make more unit tests' is not fitting because of the lack of time, infrastructure etc...

Every bug and feature will be tested/reviewed by a different developer, but that won't be done perfectly of course (we're still human :)).

My question is: Once we released the update, how do we prevent the vicious circle of testing via customers while not be able to add more unit tests?

The previous time we tried our best to test the software before and after release. After the deadline we were still searching and fixing bugs but the customer would also find some of these. So we post an update as soon as we were confident that the patch was increasing quality. We were so busy with finding bugs and fixing them that we weren't spending any time on creating unit tests.

This time we don't have a solid plan yet, hence the question. As stated before we did added some unit tests, but surely not enough. We are also looking for new colleagues but they are not easy to come by and management has rather high standards. We do have quite some candidates and it looks like we do get at least one new colleagues very soon, but it still takes time to get him/her up and running. The first thing we put the new colleague on will be creating unit tests. So the dependencies there are experience, skills and the time he/she can join the time.

Another problem that comes in hand with the lack of developers is that we are so focused on getting the bugs and features fixed that we don't have much time to spend on thinking about 'how we can improve the update process'. (I ask these questions in my own spare time).

Summary of steps I will try to take:

Try to get a tester before the release is done

Add unit tests while creating the features, if there isn't enough time, schedule them for after the release.

After releasing, if there is any regression, create unit tests when fixing the bugs.

Release more often in smaller chunks after the release, making it easier to release features and repair bugs with a minor priority.

答:
There is more to testing than unit testing.  You need to test the new features and bug fixes you created manually in a testing environment that mirrors a real-world installation as best as possible.  Having one of the other developers 'review' changes is not an appropriate level of testing for two reasons.  First, that implies they'll give it a quick look and then say 'sure, it works'.  Two, developers use software differently than end users - particularly software they wrote - so they may not catch problems that an end user will immediately see.  Ideally you need someone who is not a developer to run through a checklist of tests to confirm your change is working correctly before a customer ever gets their hands on it.  I suspect if you were testing thoroughly in this manner, you would never have been getting 3 patches a week out.

Expanding this a bit based on your other question...

You also need to get into a release schedule.  Multiple releases a week is too high a pace to give you the time necessary to test a release thoroughly.  This is especially true if you are seeing a problem of your patches introducing new bugs.  If you are concerned that a customer will be held up waiting for a fix if a bug is introduced in a patch, better to give them an easy way to revert to the previous working version and have them wait until the next scheduled release date so you are not rushing things out the door.  My advice to you is to attempt a 1 month release schedule at first.  Company management may resist this because they want to appear 'responsive' to customers.  Having seen that attitude in companies I have worked for, I assure you, you are not doing the customer any favors by giving them improperly tested updates.  Many non-technical decision makers will push back against doing this because they don't undestand the problem.  Unfortunately all you can do is lead a horse to water... you can't make it drink.  Its your professional responsibility to tell them the wise course of action, and not yours if they won't follow it.


答:
The answer is more tests. Unfortunately, that isn't the answer you want to hear, but it really is the only solution. As you noted, the last roll-out went disastrously, which is most detrimental to customer satisfaction. It would be better to build a solid product with fewer new features than to build a whole bunch of buggy features on a buggy base. "This is a great new feature, but unfortunately it deleted all my data!"

For the as-yet-unwritten features, definitely write tests (and my opinion would be to at least do test-first programming if not full TDD). These are greenfields, so you can make the efforts to make them good from the start. Prioritize the new features, and do the most important first. Less important features will be less missed for a release if they work well.

For the already-written features, prioritize those into a list, and work your way through that as well. Obviously your progress will be dependent on how important each feature is and how important developing new features is, but make time to work through this list as you can.

For the bugs, especially for the bugs, write tests when you fix them. The test can just be a guard against what you fixed to start, but at least you know you won't make that mistake again.

I do have personal experience with this type of workflow, and I can say that I have had positive results. It can be a real slog, but it works out for the better.

Title: How to prevent the vicious circle of testing via customer

Body:
I recently asked this question and this comment and made me ponder the whole process of releasing an update to the customers. The next update for our software is planned and the previous time it went horribly wrong because of regression, bad testing, etc...

This time we want to prevent the scenario that we test via our customer and made some unit tests and other minor improvements.
However, there is not enough time to make unit tests for all the features that lack unit tests or the features that need to be build yet.
So the answer for this question 'Make more unit tests' is not fitting because of the lack of time, infrastructure etc...

Every bug and feature will be tested/reviewed by a different developer, but that won't be done perfectly of course (we're still human :)).

My question is: Once we released the update, how do we prevent the vicious circle of testing via customers while not be able to add more unit tests?

The previous time we tried our best to test the software before and after release. After the deadline we were still searching and fixing bugs but the customer would also find some of these. So we post an update as soon as we were confident that the patch was increasing quality. We were so busy with finding bugs and fixing them that we weren't spending any time on creating unit tests.

This time we don't have a solid plan yet, hence the question. As stated before we did added some unit tests, but surely not enough. We are also looking for new colleagues but they are not easy to come by and management has rather high standards. We do have quite some candidates and it looks like we do get at least one new colleagues very soon, but it still takes time to get him/her up and running. The first thing we put the new colleague on will be creating unit tests. So the dependencies there are experience, skills and the time he/she can join the time.

Another problem that comes in hand with the lack of developers is that we are so focused on getting the bugs and features fixed that we don't have much time to spend on thinking about 'how we can improve the update process'. (I ask these questions in my own spare time).

Summary of steps I will try to take:

Try to get a tester before the release is done

Add unit tests while creating the features, if there isn't enough time, schedule them for after the release.

After releasing, if there is any regression, create unit tests when fixing the bugs.

Release more often in smaller chunks after the release, making it easier to release features and repair bugs with a minor priority.


答:
Licence isn't some property of code, it's a [offer of] contract between you and somebody else, where you grant them licence to use your copyrighted item under some condictions.

First, you may do whatever you want with the code as long as it's only yours.

Second, any piece of code may have multiple licences attached to it depending on how and to whom the author has distributed it. You may have the exact same code with one licence available to everyone, with another (more permissive) licence to people who pay you money for those extra permissions, and a completely different licence to a single specific company. The permissions depend your relations/agreements with the other party, not only on the code itself.

Third, for any licence of any code, it's conditions apply to you only if you need the licence to grant you some permission - i.e., if you want to modify&distribute something where someone else owns the copyright. (Or you have a specific signed contract, but that's more common in B2B enterprise issues). If you want to do something where you don't need permission - the licence doesn't [need to] apply.

Fourth, for software do note that many things change if multiple people are authors of parts of it - e.g., if other people make small improvements and want to redistribute the combined project. Then the result is not your code anymore (e.g., it's not 100% yours), and in order to make it work, you need to take a look at the software-specific licences (not the creative commons family) which handle those issues as well.


问:
Are null references really a bad thing?
I've heard it said that the inclusion of null references in programming languages is the "billion dollar mistake".  But why?  Sure, they can cause NullReferenceExceptions, but so what?  Any element of the language can be a source of errors if used improperly.

And what's the alternative?  I suppose instead of saying this:

Customer c = Customer.GetByLastName("Goodman"); // returns null if not found
if (c != null)
{
    Console.WriteLine(c.FirstName + " " + c.LastName + " is awesome!");
}
else { Console.WriteLine("There was no customer named Goodman.  How lame!"); }
```

<p>You could say this:</p>

<pre class="lang-cs prettyprint-override"><code>if (Customer.ExistsWithLastName("Goodman"))
{
    Customer c = Customer.GetByLastName("Goodman") // throws error if not found
    Console.WriteLine(c.FirstName + " " + c.LastName + " is awesome!");
}
else { Console.WriteLine("There was no customer named Goodman.  How lame!"); }
</code>```

But how is that better?  Either way, if you forget to check that the customer exists, you get an exception.

I suppose that a CustomerNotFoundException is a bit easier to debug than a NullReferenceException by virtue of being more descriptive.  Is that all there is to it?

答:
A null pointer is a tool

not an enemy. You just ought to use 'em right.

Think just minute about how long it takes to find and fix a typical invalid pointer bug, compared to locating and fixing a null pointer bug. It's easy to check a pointer against null. It is a PITA to verify whether or not a non-null pointer points to valid data.

If still not convinced, add a good dose of multithreading to your scenario, then think again.

Moral of the story: Don't throw the kids with the water. And don't blame the tools for the accident. The man who invented the number zero long time ago was quite clever, since that day you could name the "nothing". The null pointer is not so far away from that.

EDIT: Although the NullObject pattern seems to be a better solution than references that may be null, it introduces problems on its own:

A reference holding a NullObject should (according to the theory) do nothing when a method is called. Thus, subtle errors can be introduced due to errorneously unassigned references, which now are guaranteed to be non-null (yehaa!) but perform an unwanted action: nothing. With an NPE it is next to obvious where the problem lies. With a NullObject that behaves somehow (but wrong), we introduce the risk of errors being detected (too) late. This is not by accident similar to an invalid pointer problem and has similar consequences: The reference points to something, that looks like valid data, but isn't, introduces data errors and can be hard to track down. To be honest, in these cases I would without a blink prefer an NPE that fails immediately, now, over a logical/data error which suddenly hits me later down the road. Remember the IBM study about cost of errors being a function of at which stage they are detected?

The notion of doing nothing when a method is called on a NullObject does not hold, when a property getter or a function is called, or when the method returns values via out. Let's say, the return value is an int and we decide, that "do nothing" means "return 0". But how can we be sure, that 0 is the right "nothing" to be (not) returned? After all, the NullObject should not do anything, but when asked for a value, it has to react somehow. Failing is not an option: We use the NullObject to prevent the NPE, and we surely won't trade it against another exception (not implemented, divide by zero, ...), do we? So how do you correctly return nothing when you have to return something?

I can't help, but when someone tries to apply the NullObject pattern to each and every problem, it looks more like trying to repair one mistake by doing another one. It is without much doubt a good and useful solution in some cases, but it surely isn't the magic bullet for all cases.

Title: Are null references really a bad thing?


答:
Focus on just doing a good job with your tasks.

Work on being a better developer. Solve your own imperfections before you worry about that of the company.

Create a reputation in the company as a person who can be trusted with an assignment. Test your own work. Write unit tests for your changes. Demonstrate the behavior of a professional developer that creates quality software.

When time comes they will ask you "How do you do it? Everyone else is far less effective".

Once you have their ear. They will be willing to listen, but first you have to demonstrate that quality is possible.

The first step in introducing change in the people around you. Is to first change yourself. Quality software starts first with the individual.

The benefit in changing how you work is that it will attract like minded people. One advantage is that it often attracts people from outside the company. While your current employer may not embrace the new you and adopt an attitude of quality control. There are other businesses that will open doors for you. You will find that you have more in common with their goals, then the goals of your current employer.


问:
Differences between HTML templating systems
I'm looking at backbone.js and noticed that it supports various templating systems (they specifically refer to Mustache.js, Haml-js, and Eco, but I understand it can support even more)(like Pure and dust.js)

Why are there so many of these? What makes one better or different to the others? Can anyone shed light on what their individual strengths and weaknesses are?

答:
I'm currently going for Mustache.

The main reason, is that it's available in Ruby, JavaScript, Python, Erlang, node.js, PHP, Perl, Objective-C, Java, .NET, Android, C++, Go, Lua, ooc, ActionScript, ColdFusion, Scala, Clojure, Fantom, CoffeeScript, D, Haskell, XQuery, ASP, Io, Dart, and Haxe.

This means you can share your templates between your JS and whatever backend language you're using, which is very useful if you want to render your layout in backend and rerender it in frontend when updating. While some other template systems also have implementations in other languages than their initial implementation, Mustache is the only one with multiple official implementations.

Mustache templates also have a very simple syntax that don't add much clutter to your HTML and actually still look like HTML (unlike HAML).


答:
You need to test intelligently. For now, make a dependency tree of the files/features/components in the system. Mark the ones that have had work done on them, test those and any other files/features/components that take dependencies on them.

What this allows you to do is write, or perform, tests surgically. You need:

Testers

From what I am hearing, you don't have a lot of test code. You need bodies in seats, that are not developers (ideally people closest to what a customer is, but with test experience/skills). These people should hammer the features, that you've identified need testing, with all kinds of well though out test cases. Test case design/selection is a rigorous task in and of itself (all to many times have I seen redundant tests in test plans).

Test Code

Again, unit tests can be helpful, but they are often too granular for the situation you're in. You need integration tests. Write rigorous test cases for the inputs/outputs for your customer facing components/services. You'll get better test coverage in a short timespan with targeted, repeatable, integration tests. In the short term, try not to overlap integration test code with test cases being performed by testers unless it is a critical component.


答:
I would guess the two most likely reasons are:

That the getters and setters were autogenerated by the authours tooling.

The variable was initial set to be a more restricted scope and someone else has changed it.

Title: Why do some projects have getters and setters for public instance variables?

Body:
I was looking into an open-source game framework project written in Java. It has several classes that:

Have public instance variables.

Have getter/setters for such variables.

Generally, I write getters/setters when I want to encapsulate some behavior that occurs when a property is modified.

However, looking at the code, it literally goes something like this:

```<code>public class Test {
    public int value;
    public void setValue(x) {
        value = x;
    }
    public void getValue() {
        return value;
    }
}
</code>```

Then I thought about checking out the rest of the framework and see how do they modify such value, which may give me a hint on why did they do the above.

From what I've seen, they do it like this:

```<code>object.value = 100;
</code>```

Without using the getters/setters.

So now I'm not sure what was the point of creating getters/setters.

So, my question is, is there a reason I would want to create getters/setters for a public value, if such getters/setters don't even implement any kind of special behaviour?


答:
PhD already answered really well the comparison points, so I am gonna focus on

Why are there so many of these?

Quite a few reasons :

They have different philosophy concerning what should be in a template. Some try to force the "no logic in a template" rule, other don't care : For example, mustache is very strict, underscore let you use any sort of javascript in the template.

They were made by different people who had different need. Some wanted a very generic template system implementable in any language, other only needed javascript and optimised for that.

Some only needed the template to generate HTML, and optimized the syntax for that. Other made them capable of outputting any text content, but with a syntax that could be considered less confortable.

It all boil down to the definition of design: "Design is the art of balancing conflicting requirements". People who designed the various template engine had different priorities, so they produced different designs.

Title: Differences between HTML templating systems

Body:
I'm looking at backbone.js and noticed that it supports various templating systems (they specifically refer to Mustache.js, Haml-js, and Eco, but I understand it can support even more)(like Pure and dust.js)

Why are there so many of these? What makes one better or different to the others? Can anyone shed light on what their individual strengths and weaknesses are?


问:
How does one decide if a data object type should be designed to be immutable?
I love the immutable "pattern" because of its strengths, and in the past I have found it beneficial to design systems with immutable data types (some, most or even all). Often when I do so, I find myself writing fewer bugs and debugging is much easier.

However, my peers in general shy away from immutable. They are not inexperienced at all (far from it), yet they write data objects the classic way - private members with a getter and a setter for every member. Then usually their constructors take no arguments, or maybe just take some arguments for convenience. So often, creating an object looks like this:

```<code>Foo a = new Foo();
a.setProperty1("asdf");
a.setProperty2("bcde");
</code>```

Maybe they do that everywhere. Maybe they don't even define a constructor that takes those two strings, no matter how important they are. And maybe they don't change the value of those strings later and never need to. Clearly if those things are true, the object would be better designed as immutable, right? (constructor takes the two properties, no setters at all).

How do you decide if an object type should be designed as immutable? Is there a good set of criteria to judge it by?

I currently am debating whether to switch a few data types in my own project to immutable, but I would have to justify it to my peers, and the data in the types might (VERY rarely) change - at which time you can of course change it the immutable way (create a new one, copying the properties from the old object except for the ones that you want to change). But I'm not sure if this is just my love for immutables showing through, or if there is an actual need for/benefit from them.

答:
And maybe they don't change the value of those strings later and never need to. Clearly if those things are true, the object would be better designed as immutable, right?

Somewhat counter-intuitively, never needing to change the strings later on is a pretty good argument that it doesn't matter if the objects are immutable or not.  The programmer is already treating them as effectively immutable whether the compiler enforces it or not.

Immutability doesn't usually hurt, but it doesn't always help either.  The easy way to tell if your object might benefit from immutability is if you ever need to make a copy of the object or acquire a mutex before changing it.  If it never changes, then immutability doesn't really buy you anything, and sometimes makes things more complicated.

You do have a good point about the risk of constructing an object in an invalid state, but that's really a separate issue from immutability.  An object can be both mutable and always in a valid state after construction.

The exception to that rule is that since Java supports neither named parameters nor default parameters, it can sometimes get unwieldy to design a class that guarantees a valid object just using overloaded constructors.  Not so much with the two-property case, but then there's something to be said for consistency as well, if that pattern is frequent with similar but larger classes in other parts of your code.


答:
There is much more to testing than unit testing, regression testing, or exploratory testing. Unit testing only has so much value, writing tests that the programmer knows will pass now, is only useful to populate a regression suite or to help guide you before the code is written as in Test Driven Development.

There is a great diagram on Lisa Crispin's site that talks about the "Agile test quadrants". It talks about four quadrants split between

Business Facing vs Technology Facing

(Functional Test etc.) / (Scenarios etc.)

Supporting the Team vs Critiquing the Product

(Unit tests etc.) / (ility testing eg scalability, usability etc.)

There is a good book, Agile Testing that talks a lot about all the other types of testing apart form Unit testing. It is not easy to do this, especially under time pressures and it is hard for all programmers, and very hard for some, to think in the analytical way necessary to test using this approach but it is the best way I have found so far.

By analysing each new feature by at least considering each quadrant you can decide quickly what needs to be done and what can be left out or deferred.

To be able to decide what needs to be done you really need a good idea of the state of your product. What areas are a concern? What features do you know are not as reliable as the rest of the product? You also need a way to gain confidence in a candidate for release. How long does it take between writing a new functions and the developer being able to see if it has broken anything else? How long does it take to be able to get a build up and running and see if the product works as expected, not just seeing that the function returns the 'correct' value, but interacting with the system as the user will and seeing if it acts as I expect?

The other non-testing part of testing is that when you are considering the other types of testing (not unit testing), are you validating the results against what the user is expecting? Are you doing hall way usability testing (getting some one not in your team, who doesn't know the code or what the feature is 'supposed' to do to try interacting with the system to see if it makes sense)? Do your User Stories (or high level sets of tasks to complete) talk about the end user and what they expect to happen and why they are using the product in this way, what are they trying to achieve, what do they care about? Are you checking that what you are building is what the user needs or just some engineered approximation of a feature set that bares a resemblance to what they asked for?

If an organisation thinks that testing (the department / team / individuals / or developers that are doing it this week) is doing such a poor job that it has become a problem for the business (sometimes it is appropriate to put out buggy software, professional software developers don't like it, it feels like someone scratching a blackboard, but that doesn't mean it's wrong) then I would guess that most of the time it isn't a problem that can be solved by any extra testing, test strategy, or 'agile' practices but it is the development practices that need looking at, the attitudes or the bureaucracy and process around requirements and developing and people not realising the consequences of their current practices.


答:
Let's say you are doing the interior design in your living room: you install a fancy chandelier on your ceiling and plug in a classy matching floor lamp. A year later your lovely wife decides she'd like the room a little less formal. Which lighting fixture is going to be easier to change?

The idea behind DI is to use the "plug-in" approach everywhere. This may not seem like a big deal if you live in a simple shack with no drywall and all the electrical wires exposed. (You're a handyman -- you can change anything!) And similarly, on a small & simple application, DI can add more complication than it is worth.

But for a large and complex application, DI is indispensable for long-term maintenance. It allows you to "unplug" entire modules from your code (the database backend, for example), and exchange them with different modules that accomplish the same thing but do it in an entirely different way (a cloud storage system, for example).

BTW, a discussion of DI would be incomplete without a recommendation of Dependency Injection in .NET, by Mark Seeman. If you are familiar with .NET and you ever intend to be involved in large-scale SW development, this is an essential read. He explains the concept far better than I can.

Let me leave you with one last essential characteristic of DI that your code example overlooks. DI allows you to harness the vast potential of flexibility that is encapsulated in the adage "Program to interfaces". To modify your example slightly:

```<code>public void Main()
{
    ILightFixture fixture = new ClassyChandelier();
    MyRoom room = new MyRoom (fixture);
}
...
public MyRoom(ILightFixture fixture)
{
    this.MyLightFixture = fixture ;
}
</code>```

But NOW, because MyRoom is designed to the ILightFixture interface, I can easily go in next year and change one line in the Main function ("inject" a different "dependency"), and I instantly get new functionality in the MyRoom (without having to rebuild or redeploy MyRoom, if it happens to be in a separate library. This assumes, of course, that all your ILightFixture implementations are designed with Liskov Substitution in mind). All, with just a simple change:

```<code>public void Main()
{
    ILightFixture fixture = new MuchLessFormalLightFixture();
    MyRoom room = new MyRoom (fixture);
}
</code>```

Plus, I can now Unit Test MyRoom (you are unit testing, right?) and use a "mock" light fixture, which allows me to test MyRoom entirely independent of ClassyChandelier.

There are many more advantages, of course, but these are the ones that sold the idea to me.

Title: Understanding dependency injection

Body:
Let's say you are doing the interior design in your living room: you install a fancy chandelier on your ceiling and plug in a classy matching floor lamp. A year later your lovely wife decides she'd like the room a little less formal. Which lighting fixture is going to be easier to change?

The idea behind DI is to use the "plug-in" approach everywhere. This may not seem like a big deal if you live in a simple shack with no drywall and all the electrical wires exposed. (You're a handyman -- you can change anything!) And similarly, on a small & simple application, DI can add more complication than it is worth.

But for a large and complex application, DI is indispensable for long-term maintenance. It allows you to "unplug" entire modules from your code (the database backend, for example), and exchange them with different modules that accomplish the same thing but do it in an entirely different way (a cloud storage system, for example).

BTW, a discussion of DI would be incomplete without a recommendation of Dependency Injection in .NET, by Mark Seeman. If you are familiar with .NET and you ever intend to be involved in large-scale SW development, this is an essential read. He explains the concept far better than I can.

Let me leave you with one last essential characteristic of DI that your code example overlooks. DI allows you to harness the vast potential of flexibility that is encapsulated in the adage "Program to interfaces". To modify your example slightly:

public void Main()
{
    ILightFixture fixture = new ClassyChandelier();
    MyRoom room = new MyRoom (fixture);
}
...
public MyRoom(ILightFixture fixture)
{
    this.MyLightFixture = fixture ;
}

But NOW, because MyRoom is designed to the ILightFixture interface, I can easily go in next year and change one line in the Main function ("inject" a different "dependency"), and I instantly get new functionality in the MyRoom (without having to rebuild or redeploy MyRoom, if it happens to be in a separate library. This assumes, of course, that all your ILightFixture implementations are designed with Liskov Substitution in mind). All, with just a simple change:

public void Main()
{
    ILightFixture fixture = new MuchLessFormalLightFixture();
    MyRoom room = new MyRoom (fixture);
}

Plus, I can now Unit Test MyRoom (you are unit testing, right?) and use a "mock" light fixture, which allows me to test MyRoom entirely independent of ClassyChandelier.

There are many more advantages, of course, but these are the ones that sold the idea to me.


问:
A* with possible multiple paths
I am currently studying pathfinding and I came across A* algorithm from this site https://github.com/qiao/PathFinding.js

I tried to test A* with bi-directional and it is working great.

What I wanna do now is increase the path that it can make without adding more nodes in the openlist.

For example is that the algorithm was able to find a path but as you look at the results it can still generate one more path without touching the other path.

Any ideas?

答:
For finding

one more path without touching the other path

just remove the squares of the first path (except the start and ending square) from the map and run A* again.

Title: A* with possible multiple paths


问:
Is this proper OO design for C++?
I recently took a software processes course and this is my first time attempting OO design on my own. I am trying to follow OO design principles and C++ conventions. I attempted and gave up on MVC for this application, but I am trying to "decouple" my classes such that they can be easily unit-tested and so that I can easily change the GUI library used and/or the target OS. At this time, I have finished designing classes but have not yet started implementing methods.

The function of the software is to log all packets sent and received, and display them on the screen (like WireShark, but for one local process only). The software accomplishes this by hooking the send() and recv() functions in winsock32.dll, or some other pair of analogous functions depending on what the intended Target is. The hooks add packets to SendPacketList/RecvPacketList. The GuiLogic class starts a thread which checks for new packets. When new packets are found, it utilizes the PacketFilter class to determine the formatting for the new packet, and then sends it to MainWindow, a native win32 window (with intent to later port to Qt).1

Full size image of UML class diagram

Here are my classes in skeleton/header form (this is my actual code):

```<code>class PacketModel
{
protected:
    std::vector<byte> data;
    int id;
public:
    PacketModel();
    PacketModel(byte* data, unsigned int size);
    PacketModel(int id, byte* data, unsigned int size);
    int GetLen();
    bool IsValid(); //len >= sizeof(opcode_t)
    opcode_t GetOpcode();
    byte* GetData(); //returns &(data[0])
    bool GetData(byte* outdata, int maxlen);
    void SetData(byte* pdata, int len);
    int GetId();
    void SetId(int id);
    bool ParseData(char* instr);
    bool StringRepr(char* outstr);
    byte& operator[] (const int index);
};

class SendPacket : public PacketModel
{
protected:
    byte* returnAddy;
public:
    byte* GetReturnAddy();
    void SetReturnAddy(byte* addy);
};

class RecvPacket : public PacketModel
{
protected:
    byte* callAddy;
public:
    byte* GetCallAddy();
    void SetCallAddy(byte* addy);
};

//problem: packets may be added to list at any time by any number of threads
//solution: critical section associated with each packet list
class Synch
{
public:
    void Enter();
    void Leave();
};

template<class PacketType> class PacketList
{
private:
    static const int MAX_STORED_PACKETS = 1000;
public:
    static const int DEFAULT_SHOWN_PACKETS = 100;
private:
    vector<PacketType> list;
    Synch synch; //wrapper for critical section
public:
    void AddPacket(PacketType* packet);
    PacketType* GetPacket(int id);
    int TotalPackets();
};

class SendPacketList : PacketList<SendPacket>
{

};

class RecvPacketList : PacketList<RecvPacket>
{

};

class Target //one socket
{
    bool Send(SendPacket* packet);
    bool Inject(RecvPacket* packet);
    bool InitSendHook(SendPacketList* sendList);
    bool InitRecvHook(RecvPacketList* recvList);
};

class FilterModel
{
private:
    opcode_t opcode;
    int colorID;
    bool bFilter;
    char name[41];
};

class FilterFile
{
private:
    FilterModel filter;
public:
    void Save();
    void Load();
    FilterModel* GetFilter(opcode_t opcode);
};

class PacketFilter
{
private:
    FilterFile filters;
public:
    bool IsFiltered(opcode_t opcode);
    bool GetName(opcode_t opcode, char* namestr); //return false if name does not exist
    COLORREF GetColor(opcode_t opcode); //return default color if no custom color
};

class GuiLogic
{
private:
    SendPacketList sendList;
    RecvPacketList recvList;
    PacketFilter packetFilter;
    void GetPacketRepr(PacketModel* packet);
    void ReadNew();
    void AddToWindow();
public:
    void Refresh(); //called from thread
    void GetPacketInfo(int id); //called from MainWindow
};
</code>```

I'm looking for a general review of my OO design, use of UML, and use of C++ features. I especially just want to know if I'm doing anything considerably wrong.

From what I've read, design review is on-topic for this site (and off-topic for the Code Review site).

Any sort of feedback is greatly appreciated. Thanks for reading this.

答:
bool GetData(byte* outdata, int maxlen); why not returning a byte* as a result? Generaly it is bad to have an output in the parameter. You can also consider making a deticated structure to the method result.

There should be no protected fields - it is better to have protected getter and setter and private backing field (encaupsulation).

class PacketList - I am sure that there are some kind of ConcurrentLists already implemented.

What are SendPacketList and RecvPacketList clases for? They are useless.

I see that a lot of things are returning a bool value. I would consider using Exceptions handling instead.

Title: Is this proper OO design for C++?


问:
Is it acceptable within the community of developers to copy open-source software and branch it?
Is it generally, to a reasonable developer, considered morally acceptable, to take a branch of an open-source repository, and start making changes to it and calling your own? You would be taking this to another open-source.

Assume that you will link to the original. Note that this is a question of what is considered acceptable, not what is legal.

If this is okay, where is the line of how much you change that allows you to call it your own?

答:
This is a process known as 'forking' and is so acceptable, GitHub has a button for it.

So yes, feel free to fork at will.  One thing to remember: If you fix bugs/add new things in your fork, submit them to the original project.


问:
KISS principle applied to programming language design?
KISS ("keep it simple, stupid" or "keep it simple stupid", see e.g. here) is an important principle in software development, even though it apparently originated in engineering. Citing from the wikipedia article:

The principle is best exemplified by the story of Johnson handing a team of design engineers a handful of tools, with the challenge that the jet aircraft they were designing must be repairable by an average mechanic in the field under combat conditions with only these tools. Hence, the 'stupid' refers to the relationship between the way things break and the sophistication available to fix them.

If I wanted to apply this to the field of software development I would replace "jet aircraft" with "piece of software", "average mechanic" with "average developer" and "under combat conditions" with "under the expected software development / maintenance conditions" (deadlines, time constraints, meetings / interruptions, available tools, and so on).

So it is a commonly accepted idea that one should try to keep a piece of software simple (or simple stupid, in case you omit the comma) so that it easy to work on it later.

But can the KISS principle be applied also to programming language design? Do you know of any programming languages that have been designed specifically with this principle in mind, i.e. to "allow an average programmer under average working conditions to write and maintain as much code as possible with the least cognitive effort"?

If you cite any specific language it would be great if you could add a link to some document in which this intent is clearly expressed by the language designers. In any case, I would be interested to learn about the designers' (documented) intentions rather than your personal opinion about a particular programming language.

答:
A major key to maintaining "simplicity" is to recognize when complexity will be necessary, and have the parts of the system that can best deal with it, do so.  Having a single kind of object reference which makes no distinction between immutable values, mutable values, and entities, makes Java "simple", doesn't eliminate the need to distinguish between values and entities; it merely deprives programmers of tools to help them do so.

More generally, if one is trying to have a programming language or framework feature support multiple usage cases, one should ensure that there won't be any situations where different behaviors would be appropriate in different usage cases, but the compiler would be unable to tell them apart.  Adding more types to a language or framework may seem like a complication, but in many cases it may actually make things easier.

Consider, for example, the mess of rules surrounding signed and unsigned types in C.  The complexity of these rules stems from the fact that some code uses unsigned integer types to represent numbers, while other code uses them to represent members of a wrapping algebraic ring (specifically, the set of integers congruent mod 2ⁿ).  The type conversion rules behave in ways which are sometimes appropriate to one usage, and sometimes in ways appropriate to the other.  Having separate wrapping and non-wrapping types would double the number of integer types, but could simplify the rules associated with them:

Any non-ring integer type of any size may be assigned to a ring of any size; a ring may be assigned only to a ring of equal or smaller size.

Operations other than relational operators involving a non-ring integer and a ring will implicitly convert the integer to the ring type.

Rings may be explicitly cast to numbers or to larger rings; the value of an unsigned ring is the smallest non-negative integer which, when added to the ring's zero, would yield the ring value.  The value of a signed ring is the smallest-magnitude integer which, when added to the ring's zero, would yield the ring value, with the negative value being preferred in case of a tie.

Except as mentioned above, rings are limited to operations with rings of the same size or smaller.

Operations on non-ring integers of different types should upcast the numbers to a type that can accommodate all values of either operand, or should be rejected by the compiler if no suitable type exists

Defining ring types would seem to double the number of integer types, but would greatly simplify the writing of portable code.  Using the same unsigned types for numbers and rings reduces the number of types, but leads to complicated rules which make it almost impossible to write efficient portable code.