1

I want to draw locations for firm type 0 and 1 from the uniform distribution, and to calculate distances between the two types by using the OOP concept in Python.

class Firm_loc:

    def __init__(self,type):
        self.type = type
        self.random_location()

    def random_location(self):
        self.location = uniform(0,1), uniform(0,1)

    def distance(self,other):
        xx = (self.location[0] - other.location[0])**2
        yy = (self.location[1] - other.location[1])**2
        return sqrt(xx+yy)

firms = [Firm_loc('Firm_type_0') for i in range(5)]
firms.extend=[Firm_loc('Firm_type_1') for i in range(5)]

Question 1: From here, I am stuck. I have to call the distance method to calcuate every distance between the two firm types (i.e. self and other) and save them onto a list. Any help would be appreciated.

Question 2: Would there be any other more shorter, efficient codes, rather than the above?

Question 3: I am trying using the concept of "self and other" in OOP because of the pair-wise calculation for two types. How would the code be rewritten in terms of the traditional procedural approach?

EDIT:

Thanks for the answers, but as for the distances, I have to have 5x5=25 distances as follows:

Firm_type_0    Firm_type_1    Distance
   f0_0            f0_1       D(f0_0, f0_1)
   f0_0            f1_1       D(f0_0, f1_1)
   f0_0            f2_1       D(f0_0, f2_1)
   f0_0            f3_1       D(f0_0, f3_1)
   ...

I think the two answers do not produce those distances.

2
  • You probably meant firms.extend([Firm_loc('Firm_type_1') for i in range(5)]). Otherwise, you are overwriting a list's extend method. Commented Oct 28, 2013 at 20:04
  • You should take a look at docs.scipy.org/doc/scipy/reference/…, specifically pdist or cdist. This will require you storing your data in numpy arrays though. Commented Oct 28, 2013 at 20:06

3 Answers 3

1

I think You should store different types into different lists. And then iterate over product of these lists and calculate distance for pairs.

import itertools
firms = [Firm_loc('Firm_type_0') for i in range(5)]
other_firms = [Firm_loc('Firm_type_1') for i in range(5)]
distances = [i.distance(j) for i, j in itertools.product(firms, other_firms)]

product produces cartesian product of input iterables.

Sign up to request clarification or add additional context in comments.

2 Comments

Thanks, but it seems that the code does not produce 25 distances.
oh sorry, missed this
1

I'm not sure I understand.

Your code seems alright, there is not much space to performance improvement in something like that, then again python isn't very good with maths anyway.

If you want to calculate the distance between pairs of firms, you need a pair lists.

firms_a = [Firm_loc('Firm_type_0') for i in range(5)]
firms_b = [Firm_loc('Firm_type_1') for i in range(5)]
all_firms = firms_a + firms_b
firm_distances = [firm_a.distance(firm_b) for firm_a, firm_b in zip(firms_a, firms_b)]
# firm_distance[0] is firms_a[0] distance to firms_b[0] and so on

The "OOP" you have used there is just very basic syntactic sugar. A procedural approach could do this:

Firm_loc.distance(firm_a, firm_b)

Which is the same of:

firm_a.distance(firm_b)

Until you start dealing with inheritance you are more likely to be doing structural programming with syntactic sugar than object oriented programming.

EDIT: To get the distance between each type_0 for each type_1:

firms_a = [Firm_loc('Firm_type_0') for i in range(5)]
firms_b = [Firm_loc('Firm_type_1') for i in range(5)]
all_firms = firms_a + firms_b
firm_distances = {
    firm_a:{
        firm_b:firm_a.distance(firm_b) for firm_b in firms_b
    }
    for firm_a in firms_a
}
# Getting the distance of two firms, always A then B
firm_a, firm_b = firms_a[2], firms_b[1]
print(firm_distances[firm_a][firm_b])

# Iterating through distances from a firm A
for firm_b, firm_distance in firm_distances[firm_a].items():
    print(firm_distance)

# Iterating through distances from a firm B
for firm_a in firm_distances:
    print(firm_distances[firm_a][firm_b])

2 Comments

Thanks, but it seems that the code does not produce 25 distances.
@BillTP then you want the distance between each type_0 and type_1. Forget about lists you need dictionaries.
1

I'm not quite sure what are you trying to accomplish... Here's an example with generators, it kinda does what you want, right? 5 x 5...

firms_a = (Firm_loc('Firm_type_0') for i in range(5))
distances = [[firm.distance(i) for i in (Firm_loc('Firm_type_1') for j in range(5))] for firm in firms_a]

About OOP question I think that OdraEncoded supplied good answer. You could put it into class method for example:

class FirmLoc:
    @classmethod
    def distance(cls, first, second):
        #body of your distance function 
    ...

What do you mean by Question 1? Where are you stuck? What do you want to accomplish?

1 Comment

Thanks. I just wanted to calculate the 25 distances. And your code produces a satisfactory result.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.