我有一个用于在蜂窝网络中生成六边形结构的代码,它的输入是所需的层数和半径..当输入到多个层时,它将生成7个六边形单元格,当它为2时它将产生19个细胞。现在我只需要提取六边形结构的外边界而没有任何内部六边形单元格。如何只生成六边形网络的外边界?
enter code here
d = input('Enter the distance')
radius = d/sqrt(3);% radius of each hexagon
tier = input('Enter the tier value');
%num = input('enter the value 0 or 1 : n_los=1 or los=0') ;
G = ((2*2*d)/10)+1; % value required to rearrange the matrix in 3 dim
di = 0;
global expected_bs;
expected_bs = (tier)^2 + (tier+1)^2 + (tier*(tier+1));
display(expected_bs);
global bs_cord; %base station co-ordinates
%bs_cord = zeros(expected_bs, 2);
bs_cord = [0 0];
t = linspace(0,2*pi,7);
% X and Y co-ordinates of 7 vertices for plotting hexagon. : TIER 1
x_ = [ 0 0 ((sqrt(3)/2)*d) ((sqrt(3)/2)*d) 0 -((sqrt(3)/2)*d) -((sqrt(3)/2)*d) ];
y_ = [ 0 d (d/2) (-d/2) -d (-d/2) (d/2) ];
% Hexagonal cells generation
for u=1:tier
g_ = u*x_;% to get first hexagon structure : x coordinate
h_ = u*y_;% to get first hexagon : y coordinate
bs = plot_cluster(g_ , h_ , t, radius ,bs );% function defined to plot the hexagon
if u > 1
m_ = u* [ 0 ((sqrt(3)/2)*d) ((sqrt(3)/2)*d) 0 -((sqrt(3)/2)*d) -((sqrt(3)/2)*d) 0 ];% to get hexagon in inclined direction
n_ = u* [ d (d/2) (-d/2) -d (-d/2) (d/2) d ];
for i=1:(u-1)
for k=1:6
inner_cell_x = (((i * m_(k))+ ((u-i) * m_(k+1)))/(u)); % ratio method to obtain the coordinates of hexagon
inner_cell_y = ((i * n_(k))+ ((u-i) * n_(k+1)))/(u);
bs = plot_cell(inner_cell_x , inner_cell_y , t, radius, bs);
end
end
end
end
bs_cord = unique(bs_cord,'rows'); % base station coordinates unique func is for eliminating the replicated coordinates
有人请帮忙
答案 0 :(得分:1)
我花了很长时间在这上面工作。我希望它运作良好。
秘诀是你需要摆脱任何重复的六边形,然后只计算那些顶点只有零或一个重叠的那些。
修改添加的响铃中心
function [X, Y, xe, ye, X0, Y0, outerCenter] = hexagon(varargin)
%% hexagon: A hexagon cell generating function
% Possible inputs
% hexagon
% Will assume a new figure is not wanted. Using this option will call
% up inputs in the command window to get information about the cells.
% hexagon(newFigure)
% Where newFigure is a logical, if true the cell will be shown on a
% new figure. If false the cell will be shown on an old figure (if
% available). Using this option will call up inputs in the command
% window to get information about the cells.
% hexagon(D, tiers)
% Where newFigure is a logical, if true the cell will be shown on a
% new figure. If false the cell will be shown on an old figure (if
% available).
% hexagon(D, tiers, newFigure)
% Where newFigure is a logical, if true the cell will be shown on a
% new figure. If false the cell will be shown on an old figure (if
% available).
%
% Outputs
% X - cell arrays of the x-coordinates of the hexagons
% Y - cell arrays of the y-coordinates of the hexagons
% xe - matrix of the x-coordinates of the verticies of the edge
% ye - matrix of the y-coordinates of the verticies of the edge
% X - cell arrays of the x-coordinates of the hexagons on the edge
% Y - cell arrays of the y-coordinates of the hexagons on the edge
%% Input parsing
global centers
%These are the centers of the hexagons, with the current tier.
%Having this in allows the program to check if there is already a
%higher tier hexagon in the same space
centers = [0, 0, -1];
if nargin == 0
newFigure = 0;
D = input('Enter the circumscribed diameter: ');
tiers = input('Enter the tier value: ');
elseif nargin == 1
newFigure = varargin{1};
D = input('Enter the circumscribed diameter: ');
tiers = input('Enter the tier value: ');
elseif nargin == 2
newFigure = 0;
D = varargin{1};
tiers = varargin{2};
elseif nargin == 3
D = varargin{1};
tiers = varargin{2};
newFigure = varargin{3};
elseif nargin > 3
error('Too many input arguements entered!')
end
x0 = input('Enter x0: ');
y0 = input('Enter y0: ');
%% Call first hexagon at origin
[X, Y] = makeHexagon(x0, y0, D, tiers);
%% Find edge of cell
[xe, ye] = findEdge(X, Y, x0, y0);
%% Find hexagons on edge
[X0, Y0] = findEdgeHexagons(X, Y, xe, ye);
%% Outside center
outerCenter = centers(:, [1,2]);
outerCenter(centers(:, 3) == 0) = [];
%% Output and Plot
disp(['A ', num2str(tiers), ' tier network of hexagons has ', num2str(numel(X)), ' elements.'])
if newFigure
fig = figure;
else
fig = gcf;
figure(fig.Number);
end
T = [X; Y]; %Prepare to plot the hexagons
plot(T{:},'LineWidth',2)
hold on
T = [X0; Y0]; %Prepare to plot the hexagons
plot( T{:},'k','LineWidth',4) %Plot the edge
plot( xe, ye,'k','LineWidth',4) %Plot the edge
axis equal
end
%% Make the hexagons
function [X, Y] = makeHexagon(x0, y0, D, tiers)
global centers
X = {};
Y = {};
%% Find out if the center has already been claimed by a higher tier
[~, ib] = ismembertol([x0, y0], centers(:, [1,2]),'ByRows',true);
if any(ib) && (tiers > centers(ib, 3))
%If it's higher tiered than a previous hexagon, then update the list
centers(ib, 3) = tiers;
elseif any(ib) && (tiers <= centers(ib, 3))
%If it's equal or lower tiered than a previous hexagon, then any space
%it could explore is already claimed
%this returns an empty cell array
return
else
%It's in completely new space
centers = [centers; x0, y0, tiers];
end
%% Make the hexagon and its children
%Get the verticies of the hexagon, note that there are 7 verticies to
%close the shape
[x, y] = hexCoords(x0, y0, D);
%if it's not at the bottom, the hexagon needs to spawn its children
if tiers > 0
%The centers will alway be at 30, 90, 150, 210, 270 and 330.
theta = linspace(0, 5*pi/3, 6)' - pi/6;
centerX = sqrt(3)*D/2*cos(theta) + x0;
centerY = sqrt(3)*D/2*sin(theta) + y0;
%Call for each child, they will be one level lower
[X, Y] = arrayfun(@(X, Y) makeHexagon(X, Y, D, tiers - 1), centerX, centerY, 'uni', 0);
%Flatten the cell arrays this combines generations 0 to tiers - 1
X = flatten(X);
Y = flatten(Y);
end
%Combine previous generations with this generation
X = horzcat(x, X{:});
Y = horzcat(y, Y{:});
%Remove any shapes that are in the same spot
[~, i, ~] = uniquetol([X', Y'], 'ByRows', true);
X = num2cell(X(:, i),1);
Y = num2cell(Y(:, i),1);
end
%% Find the edge of the cell
function [X0, Y0] = findEdge(X, Y, x0, y0)
%Remove the extra vertex for the closed shape
XY = cellfun(@(x, y) uniquetol([x(:), y(:)], 'ByRows', true), X, Y, 'uni', 0);
%convert the cell array into a matrix of x and y
XY = vertcat(XY{:});
%Find how many times each vertex is used
[~, uniqueVerticies, MappingIndicies] = uniquetol(XY, 'ByRows', true);
[n, ~, ~] = histcounts(MappingIndicies, length(uniqueVerticies));
%If it is once or twice it's on an edge
XY = XY(uniqueVerticies(n <= 2), :);
%Arrange the verticies angularly
data = sortrows([atan2(XY(:,2) - y0, XY(:,1) - x0), XY]);
%Finally, seperate them and put a final curl on it
X0 = [data(:,2); data(1,2)];
Y0 = [data(:,3); data(1,3)];
end
%% Find the hexagons on the edge of the cell
function [X0, Y0] = findEdgeHexagons(X, Y, xe, ye)
i = cellfun(@(x, y) any(ismembertol([xe(:), ye(:)], [x(:), y(:)],'ByRows',true)) , X, Y);
X0 = X(i);
Y0 = Y(i);
end
%% Map the verticies of the hexagon
function [x, y] = hexCoords(x0, y0, D)
%The centers will alway be at 0, 60, 120, 180, 240, 300 and 360
%(to close the figure).
theta = linspace(0, 2*pi, 7)';
%Convert from polar to Cartesian coordinates
x = D/2 * cos(theta) + x0;
y = D/2 * sin(theta) + y0;
end
%% Flatten the cell array and remove empty elements
function X = flatten(X)
X = X(~cellfun(@isempty, X));
i = cellfun(@iscell, X);
if any(i)
X = horzcat(X{~i}, flatten(horzcat(X{i})));
end
end