1

I have the following code snipped which works but is incredibly slow:

bps = [5; 10; 15; 20]
src = ['10.0.0.1'; '10.0.0.2'; '10.0.0.1'; '10.0.0.2']

uniqueSrc = unique(src);

sumBps = [];
for i=1:length(uniqueSrc)
    indy=find(ismember(src,uniqueSrc(i)));
    sumBps = [sumBps; sum(bps(indy))];
end

uniqueSrc = ['10.0.0.1'; '10.0.0.2']
sumBps = [20; 30]

src is a cell array containing IP adresses while one IP can occur multiple times. It is read from a file with textscan and %s. bps contains integers.

I need to sum up all integers in bps that belong to the same IP adress in src. The matching is according to the indices. So src(1) is the IP of bps(1) and so on.

The result should be a matching of the IPs to the sum of the corresponding bps values. So uniqueSrc(1) is the IP that has a sumBps(1) that is the sum of all bps values belonging to the certain IP.

While my code certainly works it is very unefficient as it seems and i wonder what would be the famous matlab one-liner to solve this problem.

Thanks in advance!

Edit: Added example input and output.

2
  • Post a small example input and the desired output Commented Mar 5, 2015 at 21:55
  • 1
    The input would be nice. How are you storing your IP addresses? Commented Mar 5, 2015 at 21:58

2 Answers 2

4

Classic use of accumarray:

%// Your inputs
bps = [5; 10; 15; 20];
src = ['10.0.0.1'; '10.0.0.2'; '10.0.0.1'; '10.0.0.2'];

%// Relevant code
[uniqueSrc,~,id] = unique(cellstr(src));
sumBps = accumarray(id, bps);

The above code probably deserves some explanation. accumarray is a function that bins or groups data together based on IDs. As such, what I did was I converted src to a cell array with cellstr, then used unique to get a list of all of the unique IP addresses in addition to assigning a unique ID to each IP address. The unique IP addresses are stored in uniqueSrc which is the first output of unique and each IP address in src is assigned a unique ID stored in id. An intricacy that not many people think about is that unique not only finds unique entries in an array, but it also returns those values sorted. From this sorted result, the IDs assigned to each element in src would follow this ordering convention. Because you want to return those IP addresses in order (it looks like it), then we don't need to think about this part. Also, I needed to convert your IP addresses into a cell array for this to work.

Once we determine these, we use accumarray where the first element is an ID for each IP address and the second element is what value each IP address maps to. By default, accumarray bins those values that share the same ID and sums them all up. That pretty much describes what exactly it is you want to do.

The output I get for your desired variables is:

>> uniqueSrc

uniqueSrc = 

    '10.0.0.1'
    '10.0.0.2'

>> sumBps

sumBps =

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

8 Comments

@eigenchris - I'm not sure if my edit came before or after your comment lol.
I'm not either, haha. I deleted it either way. Good answer, though.
The title kinda gives it away :-) . Almost posted but was looking to catenate the addresses and summed bps values into rows.
I was typing exactly the same answer, except I wrote "usual" instead of "classic". I like your term better ;-)
@TryHard - Oh! That's a good idea! If you have MATLAB R2013b or higher, try displaying them in a table.
|
1

Add my answer because I wanted to show how to catenate the IP addresses and summed bps, plus you don't need to convert to cell if you use the option rows with unique:

bps = [5; 10; 15; 20]
src = ['10.0.0.1'; '10.0.0.2'; '10.0.0.1'; '10.0.0.2'];

[strng ii jj]= unique(src,'rows');


strcat( {strng},{char(32)*ones(size(strng,1),1)},{num2str(accumarray(jj,bps))})

3 Comments

OH! Good job with the 'rows' flag!
@rayryeng Yeah but generally speaking its better to work with cell arrays unless your strings are always equal in length, which isn't a guarantee.
Yup that's why I decided to go with cells. This is certainly a toy case, but I would certainly stick with cells for variable length strings. Good going!

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.