2 % Copyright (C) 2009-2015 Peter Rakyta, Ph.D.
4 % This program is free software: you can redistribute it and/or modify
5 % it under the terms of the GNU General Public License as published by
6 % the Free Software Foundation, either version 3 of the License, or
7 % (at your option) any later version.
9 % This program is distributed in the hope that it will be useful,
10 % but WITHOUT ANY WARRANTY; without even the implied warranty of
11 % MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 % GNU General Public License
for more details.
14 % You should have received a copy of the GNU General Public License
15 % along with
this program. If not, see http:
17 %> @addtogroup basic Basic Functionalities
20 %> @brief A
class responsible
for the
Peierls and gauge transformations.
22 %> @brief A
class responsible for the
Peierls and gauge transformations.
26 properties ( Access =
protected )
27 %> String containing the name of the built-in gauge (
'LandauX',
'LandauY').
29 %> The strength of the magnetic field
for the built-in vector potentials.
31 %> Function
handle A = f( x,y) of the vector potential to be used in the calculations (A is a N x 2 vector, where N is the number of the points given by the x and y coordinates.)
37 methods ( Access =
public )
39 %% Contructor of the
class 40 %> @brief Constructor of the
class.
42 %> @
param varargin Cell array of optional parameters. For details see #InputParsing.
43 %> @
return An instance of the
class 47 obj.gauge = []; %
'LandauX',
'LandauY' gauges or []
for load from input files
48 obj.eta = 0; % eta_B = 2*pi/phi0*(rCC)^2*B;
49 obj.Vectorpotential = [];
51 obj.InputParsing( varargin{:} );
53 if isfield( obj.Opt,
'eta' )
54 obj.eta = obj.
Opt.eta;
60 if isempty( obj.Vectorpotential )
61 if isfield( obj.
Opt, 'gauge' )
62 obj.gauge = obj.
Opt.gauge;
66 obj.Vectorpotential = obj.CreateHandleForVectorpotential();
71 %% PeierlsTransformLeads
73 %> @
param Lead An instance of class
#CreateLeadHamiltonians (or a derived class) 74 function PeierlsTransformLeads( obj,
Lead )
76 if ~strcmpi(
class(
Lead),
'CreateLeadHamiltonians' )
77 supClasses = superclasses(
Lead);
79 error(['EQuUs:', class(obj.junction), ':PeierlsTransformLeads'], 'Input
Lead is not valid.');
83 if
Lead.Read( 'MagneticFieldApplied' )
84 obj.display(['EQuUs:',class(obj),':PeierlsTransformLeads: Magnetic field already applied in the
Hamiltonians']);
88 if isempty(obj.Vectorpotential)
89 obj.display(['EQuUs:',class(obj),':PeierlsTransformLeads: Vectorpotential is not set.']);
94 if ~
Lead.Read( 'HamiltoniansCreated' ) ||
Lead.Read( 'HamiltoniansDecimated' )
95 err = MException(['EQuUs:',class(obj),':PeierlsTransformLeads'], '
Hamiltonians in
Lead are not created, or they are decimated. Thus, unable to perform
Peierls transformation.');
96 save('Error_Peierls_PeierlsTransformLeads.mat');
101 H0 =
Lead.Read( 'H0' );
103 H1 =
Lead.Read( 'H1' );
105 H1_transverse =
Lead.Read( 'H1_transverse' );
106 Lead.Clear( 'H1_transverse' );
107 H1_skew_right =
Lead.Read( 'H1_skew_right' );
108 Lead.Clear( 'H1_skew_right' );
109 H1_skew_left =
Lead.Read( 'H1_skew_left' );
110 Lead.Clear( 'H1_skew_left' );
113 H0_size = size(H0,1)/2;
114 mtx_pair_potential = H0( 1:H0_size, H0_size+1:2*H0_size);
115 H0 = H0( 1:H0_size, 1:H0_size);
116 H1 = H1( 1:H0_size, 1:H0_size);
117 if ~isempty(H1_transverse)
118 H1_transverse = H1_transverse( 1:H0_size, 1:H0_size);
121 if ~isempty(H1_skew_right)
122 H1_skew_right = H1_skew_right( 1:H0_size, 1:H0_size);
125 if ~isempty(H1_skew_left)
126 H1_skew_left = H1_skew_left( 1:H0_size, 1:H0_size);
129 if norm(mtx_pair_potential,1) >= 1e-6
130 error( ['EQuUs:',class(obj),':PeierlsTransformLeads'], 'The peierls transformation with nonzero B is forbidden in the superconducting phase. Set the pair potential to zero, or use gauge transformation instead.')
131 mtx_pair_potential = mtx_pair_potential*0;
136 coordinates =
Lead.Read( 'coordinates' );
140 [sor_idx,oszlop_idx,elements] = find(H0);
142 startpoint = [coordinates.x( oszlop_idx ), coordinates.y( oszlop_idx )];
143 endpoint = [coordinates.x( sor_idx ), coordinates.y( sor_idx )];
145 fazis = obj.Peierls_phase(startpoint,endpoint);
146 fazis_mtx_H0 = sparse(sor_idx,oszlop_idx,fazis,size(H0,1), size(H0,2) );
147 elements = exp(1i*fazis).*elements;
148 H0 = sparse(sor_idx,oszlop_idx,elements,size(H0,1), size(H0,2) );
150 Lead.Write( 'fazis_mtx_H0', fazis_mtx_H0);
153 %
Peierls in the coupling of unit cells
154 [sor_idx,oszlop_idx,elements] = find(H1);
155 orientation =
Lead.Read('Lead_Orientation');
156 Hanyadik_Lead =
Lead.Read('Hanyadik_Lead' );
157 if orientation == 1 && ~isempty( Hanyadik_Lead )
158 startpoint = [coordinates.x( oszlop_idx ) , coordinates.y( oszlop_idx )];
159 endpoint = [coordinates.x( sor_idx ) - coordinates.a(1), coordinates.y( sor_idx ) - coordinates.a(2)];
161 startpoint = [coordinates.x( oszlop_idx ) + coordinates.a(1), coordinates.y( oszlop_idx ) + coordinates.a(2)];
162 endpoint = [coordinates.x( sor_idx ), coordinates.y( sor_idx )];
165 fazis = obj.Peierls_phase(startpoint,endpoint);
166 fazis_mtx_H1 = sparse(sor_idx,oszlop_idx,fazis,size(H1,1), size(H1,2) );
167 elements = exp(1i*fazis).*elements;
168 H1 = sparse(sor_idx,oszlop_idx,elements,size(H1,1), size(H1,2) );
170 Lead.Write( 'fazis_mtx_H1', fazis_mtx_H1);
173 %
Peierls in the transverse coupling of unit cells
174 if ~isempty(H1_transverse)
175 [sor_idx,oszlop_idx,elements] = find(H1_transverse);
176 startpoint = [coordinates.x( oszlop_idx ) + coordinates.b(1), coordinates.y( oszlop_idx ) + coordinates.b(2)];
177 endpoint = [coordinates.x( sor_idx ), coordinates.y( sor_idx )];
179 fazis = obj.Peierls_phase(startpoint,endpoint);
180 fazis_mtx_H1t = sparse(sor_idx,oszlop_idx,fazis,size(H1_transverse,1), size(H1_transverse,2) );
181 elements = exp(1i*fazis).*elements;
182 H1_transverse = sparse(sor_idx,oszlop_idx,elements,size(H1_transverse,1), size(H1_transverse,2) );
184 Lead.Write( 'fazis_mtx_H1t', fazis_mtx_H1t);
187 %
Peierls in the skew couling in the right direction
188 if ~isempty(H1_skew_right)
189 [sor_idx,oszlop_idx,elements] = find(H1_skew_right);
190 orientation =
Lead.Read('Lead_Orientation');
191 Hanyadik_Lead =
Lead.Read('Hanyadik_Lead' );
192 if orientation == 1 && ~isempty( Hanyadik_Lead )
193 startpoint = [coordinates.x( oszlop_idx ) + coordinates.b(1) , coordinates.y( oszlop_idx ) + coordinates.b(2)];
194 endpoint = [coordinates.x( sor_idx ) + coordinates.a(1), coordinates.y( sor_idx ) + coordinates.a(2)];
196 startpoint = [coordinates.x( oszlop_idx ) - coordinates.a(1) + coordinates.b(1), coordinates.y( oszlop_idx ) - coordinates.a(2) + coordinates.b(2)];
197 endpoint = [coordinates.x( sor_idx ), coordinates.y( sor_idx )];
200 fazis = obj.Peierls_phase(startpoint,endpoint);
201 fazis_mtx_H1_skew_right = sparse(sor_idx,oszlop_idx,fazis,size(H1_transverse,1), size(H1_transverse,2) );
202 elements = exp(1i*fazis).*elements;
203 H1_skew_right = sparse(sor_idx,oszlop_idx,elements,size(H1_transverse,1), size(H1_transverse,2) );
205 Lead.Write( 'fazis_mtx_H1_skew_right', fazis_mtx_H1_skew_right);
208 %
Peierls in the transverse coupling of unit cells
209 if ~isempty(H1_skew_left)
210 [sor_idx,oszlop_idx,elements] = find(H1_skew_left);
211 orientation =
Lead.Read('Lead_Orientation');
212 Hanyadik_Lead =
Lead.Read('Hanyadik_Lead' );
213 if orientation == 1 && ~isempty( Hanyadik_Lead )
214 startpoint = [coordinates.x( oszlop_idx ) + coordinates.b(1) , coordinates.y( oszlop_idx ) + coordinates.b(2)];
215 endpoint = [coordinates.x( sor_idx ) - coordinates.a(1), coordinates.y( sor_idx ) - coordinates.a(2)];
217 startpoint = [coordinates.x( oszlop_idx ) + coordinates.a(1) + coordinates.b(1), coordinates.y( oszlop_idx ) + coordinates.a(2) + coordinates.b(2)];
218 endpoint = [coordinates.x( sor_idx ), coordinates.y( sor_idx )];
221 fazis = obj.Peierls_phase(startpoint,endpoint);
222 fazis_mtx_H1_skew_left = sparse(sor_idx,oszlop_idx,fazis,size(H1_transverse,1), size(H1_transverse,2) );
223 elements = exp(1i*fazis).*elements;
224 H1_skew_left = sparse(sor_idx,oszlop_idx,elements,size(H1_transverse,1), size(H1_transverse,2) );
226 Lead.Write( 'fazis_mtx_H1_skew_left', fazis_mtx_H1_skew_left);
232 H0 = [H0, mtx_pair_potential; mtx_pair_potential', -conj(H0)];
233 H1 = [H1, zeros(size(H1)); zeros(size(H1')), -conj(H1)];
234 H1_transverse = [H1_transverse, zeros(size(H1_transverse)); zeros(size(H1_transverse')), -conj(H1_transverse)];
238 Lead.Write( 'H0', H0 );
239 Lead.Write( 'H1', H1 );
240 Lead.Write( 'H1adj', H1' );
241 Lead.Write( 'H1_transverse', H1_transverse );
242 Lead.Write( 'H1_skew_right', H1_skew_right );
243 Lead.Write( 'H1_skew_left', H1_skew_left );
244 Lead.Write( 'MagneticFieldApplied', 1 );
245 %Surface_tmp.Write( 'q', q);
251 %> @brief Algorithm to perform
Peierls transformation in Hamiltonian stored in the
#CreateHamiltonians object. 253 function PeierlsTransform( obj, CreateH )
256 supClasses = superclasses(CreateH);
257 if sum( strcmp( supClasses,
'CreateHamiltonians' ) ) == 0
258 error([
'EQuUs:',
class(obj.junction),
':PeierlsTransform'],
'Input CreateH is not valid.');
262 if CreateH.Read(
'MagneticFieldApplied' )
263 obj.display([
'EQuUs:',
class(obj),
':PeierlsTransform: Magnetic field already applied in the Hamiltonians'], 1);
267 if isempty(obj.Vectorpotential)
268 obj.
display(['EQuUs:',class(obj),':PeierlsTransform: Vectorpotential is not set.']);
273 err = MException(['EQuUs:',class(obj),':PeierlsTransform'], '
Hamiltonians in are not created, or they are decimated. Thus, unable to perform
Peierls transformation.');
274 save('Error_Peierls_PeierlsTransform.mat');
280 Hamiltoni = CreateH.
Read( NameOfH );
281 Hamiltoni_transverse = CreateH.
Read( NameOfH_transverse );
282 CreateH.
Clear( NameOfH );
283 CreateH.
Clear( NameOfH_transverse );
289 if ~isempty(Hamiltoni_transverse)
295 if norm(mtx_pair_potential,1) >= 1e-6
296 error( 'The peierls transformation with nonzero B is forbidden in the superconducting phase. Set the pair potential to zero, or use gauge transformation instead.')
297 mtx_pair_potential = mtx_pair_potential*0;
302 %
Peierls in the scattering region
303 [sor_idx,oszlop_idx,elements] = find(Hamiltoni);
306 fazis = obj.Peierls_phase(startpoint,endpoint);
308 fazis_mtx = sparse(sor_idx,oszlop_idx,fazis,size(Hamiltoni,1), size(Hamiltoni,2) );
309 elements = exp(1i*fazis).*elements;
310 Hamiltoni = sparse(sor_idx,oszlop_idx,elements,size(Hamiltoni,1), size(Hamiltoni,2) );
315 %
Peierls in the transverse coupling of the scattering region
316 if ~isempty(Hamiltoni_transverse)
317 [sor_idx,oszlop_idx,elements] = find(Hamiltoni_transverse);
320 fazis = obj.Peierls_phase(startpoint,endpoint);
322 fazis_mtx_t = sparse(sor_idx,oszlop_idx,fazis,size(Hamiltoni_transverse,1), size(Hamiltoni_transverse,2) );
323 elements = exp(1i*fazis).*elements;
324 Hamiltoni_transverse = sparse(sor_idx,oszlop_idx,elements,size(Hamiltoni_transverse,1), size(Hamiltoni_transverse,2) );
331 Hamiltoni_tmp = sparse([],[],[], size(Hamiltoni,1)*2, size(Hamiltoni,2)*2 );
332 Hamiltoni_transverse_tmp = sparse([],[],[], size(Hamiltoni_transverse,1)*2, size(Hamiltoni_transverse,2)*2 );
338 if ~isempty(Hamiltoni_transverse)
343 Hamiltoni = Hamiltoni_tmp;
344 Hamiltoni_transverse = Hamiltoni_transverse_tmp;
347 CreateH.
Write( NameOfH, Hamiltoni );
348 CreateH.
Write( NameOfH_transverse, Hamiltoni_transverse );
350 %Way2Hamiltonian.
Write( '
q',
q);
353 %% gaugeTransformation
354 %> @brief Algorithm to perform gauge transformation on Green's function and/or on Hamiltonian.
355 %> @
param mtx The matrix of the Green's function or the Hamiltonian.
356 %> @
param coordinates An instance of structure
#coordinates containing the site coordinates 357 %> @
param gauge_field Function
handle S = f( x,y) of the gauge transformation. (S is a N x 1 vector, where N is the number of the points given by the x and y
coordinates.)
358 %> @
return Returns with the transformaed matrix.
367 mtx_size = size(mtx,1);
369 warning( [
'EQuUs:',
class(obj.junction),
':gaugeTransformation'],
'The coordinates and matrix elements do not correspond to each other.' )
373 % "u" and "v" like components must be transformed differently in BdG theory
387 ret = Umtx * mtx * Umtx';
391 %% gaugeTransformationOnLead
392 %> @brief Algorithm to perform gauge transformation in the
Hamiltonians of a lead. The transformed matrices are stored within the input class.
393 %> @
param Lead An instance of class
#CreateLeadHamiltonians (or a derived class) 394 %> @
param gauge_field Function
handle S = f( x,y) of the gauge transformation. (S is a N x 1 vector, where N is the number of the points given by the x and y
coordinates.)
397 if ~strcmpi(
class(
Lead),
'CreateLeadHamiltonians' )
398 supClasses = superclasses(
Lead);
400 error(['EQuUs:', class(obj.junction), ':gaugeTransformationOnLead'], 'Input
Lead is not valid.');
416 orientation =
Lead.
Read('Lead_Orientation');
417 Hanyadik_Lead =
Lead.
Read('Hanyadik_Lead' );
420 if orientation == 1 && ~isempty( Hanyadik_Lead )
430 H0size = size(H0, 1);
436 H_tmp = [H0,H1;H1adj,H0];%
437 H_tmp = obj.gaugeTransformation( H_tmp, coordinates_tmp,
gauge_field );
440 H0 = H_tmp(1:H0size,1:H0size);
441 H1 = H_tmp(1:H0size,H0size+1:end);
442 H1adj = H_tmp(H0size+1:end,1:H0size);
448 % gauge transformation of the transverse H1
449 H1_transverse =
Lead.
Read('H1_transverse');
454 H_tmp = [sparse([],[],[],size(H1_transverse,2), size(H1_transverse,1)), H1_transverse; ...
455 H1_transverse', sparse([],[],[],size(H1_transverse,1), size(H1_transverse,2))];
457 H_tmp = obj.gaugeTransformation( H_tmp, coordinates_tmp,
gauge_field );
458 H1_transverse = H_tmp( 1:size(H1_transverse,2), size(H1_transverse,1)+1:end );
459 Lead.
Write( 'H1_transverse', H1_transverse);
463 %gauge transformation of the transverse momentum
464 %
q = Surface_tmp.
Read('
q');
465 % identity_mtx = sparse(1:size(H1_transverse,1),1:size(H1_transverse,1),1, size(H1_transverse,1), size(H1_transverse,2) );
470 % H_tmp = [sparse([],[],[],size(identity_mtx,2), size(identity_mtx,1)), identity_mtx; ...
471 % identity_mtx', sparse([],[],[],size(identity_mtx,1), size(identity_mtx,2))];
473 % H_tmp = gaugeTransformation( H_tmp, coordinates_tmp,
gauge_field );
474 % identity_mtx = H_tmp( 1:size(H1_transverse,2), size(H1_transverse,1)+1:end );
475 %
q =
q - angle( diag(identity_mtx) );
486 %> @brief Creates a clone of the present
object.
487 %> @return Returns with the cloned
object.
490 'Vectorpotential', obj.Vectorpotential);
494 %% setVectorPotential
495 %> @brief Use to set the
handle for the vector potential.
496 %> @
param vectorpot Function
handle A = f( x,y) of the vector potential to be used in the calculations (A is a N x 2 vector, where N is the number of the points given by the x and y
coordinates.)
497 function setVectorPotential( obj, vectorpot )
498 obj.Vectorpotential = vectorpot;
505 methods ( Access = protected )
508 %> @brief Calculates the
Peierls phase along bonds.
511 %> @return Returns with the peierls phases
512 function fazis = Peierls_phase(obj, startpoint, endpoint)
514 if obj.
Opt.Linear_Regression_in_B
515 A1 = obj.Vectorpotential(startpoint(:,1),startpoint(:,2));
516 A2 = obj.Vectorpotential(endpoint(:,1),endpoint(:,2));
517 fazis = 0.5*(A1(:,1)+A2(:,1)).*(endpoint(:,1)-startpoint(:,1)) + 0.5*(A1(:,2)+A2(:,2)).*(endpoint(:,2)-startpoint(:,2));
521 % the following is not vectorized, and is obsolete !!!! TODO
522 fazis = zeros( size(startpoint,1), 1);
523 for idx = 1:length(fazis)
524 if ~(startpoint(1) == endpoint(1))
525 dx = (endpoint(idx,1)-startpoint(idx,1))/100;
526 int_array = startpoint(idx,1):dx:endpoint(idx,1);
527 Ind = max(size(int_array));
532 A_temp = obj.Vectorpotential(x, y_temp(x,startpoint(idx,:),endpoint(idx,:)));
536 fazis(idx) = trapz(int_array,A);
540 if obj.
Opt.my_own_potential
541 fazis = zeros( size(startpoint,1), 1);
542 for idx = 1:length(fazis)
543 if ~(startpoint(idx,2) == endpoint(idx,2) )
544 dy = (endpoint(idx,2)-startpoint(idx,2))/100;
545 int_array = startpoint(idx,2):dy:endpoint(idx,2);
546 Ind = max(size(int_array));
551 A_temp = obj.Vectorpotential(x_temp(y,startpoint(idx,:),endpoint(idx,:)), y);
555 fazis(idx) = fazis(idx) + trapz(int_array,A);
560 function x = x_temp(y,startpoint,endpoint)
561 x = endpoint(1) + (startpoint(1)-endpoint(1))/(endpoint(2)-startpoint(2))*(endpoint(2)-y);
563 function y = y_temp(x,startpoint,endpoint)
564 y = endpoint(2) + (startpoint(2)-endpoint(2))/(endpoint(1)-startpoint(1))*(endpoint(1)-x);
568 %% CreateHandleForVectorpotential
569 %> @brief Creates function handles for in-built Vector potentials in a gauge given by attribute
#Opt.gauge. 570 %> @
return Returns A
function handle 571 function HandleForA = CreateHandleForVectorpotential( obj )
574 if ~isempty( obj.gauge )
575 if strcmpi( obj.gauge, 'LandauX' )
576 HandleForA = @(x,y)([-obj.eta*y;0]);
577 elseif strcmpi( obj.gauge, 'LandauY' )
578 HandleForA = @(x,y)([0;obj.eta*x]);
589 end % methods protected
593 methods ( Access = protected )
597 %> @brief Parses the optional parameters for the class constructor.
599 %> @
param 'Vectorpotential' Function
handle A = f( x,y) of the vector potential to be used in the calculations (A is a N x 2 vector, where N is the number of the points given by the x and y
coordinates.)
601 p_validating = inputParser;
602 p_validating.addParameter('Vectorpotential', []);
605 obj.Vectorpotential = p_validating.Results.Vectorpotential;
610 end % methods
private function InputParsing(varargin)
Parses the optional parameters for the class constructor.
function CreateClone(varargin)
Creates a clone of the present class.
Property HamiltoniansCreated
A logical value. True if the Hamiltonian was created, false otherwise.
A class containing methodes for displaying several standard messages.
function Write(MemberName, input)
Sets the value of an attribute in the class.
Structure Opt contains the basic computational parameters used in EQuUs.
Class to create and store Hamiltonian of the translational invariant leads.
Property MagneticFieldApplied
A logical value. True if the vector potential was incorporated into the Hamiltonian or false otherwis...
function display(message, nosilent)
Displays output messages on the screen.
Property coordinates
An instance of the structure coordinates.
function Transport(Energy, B)
Calculates the conductance at a given energy value.
function Hamiltonians(varargin)
Function to create the custom Hamiltonians for the 1D chain.
Property q
A transverse momentum.
Property fazis_mtx_scatter
The matrix of the Peierls phases.
function Clear(MemberName)
Clears the value of an attribute in the class.
A class to calculate the Green functions and self energies of a translational invariant lead The nota...
Property varargin
list of optional parameters (see http://www.mathworks.com/help/matlab/ref/varargin....
Structure param contains data structures describing the physical parameters of the scattering center ...
Property Hscatter_transverse
The matrix of the Hamiltonian corresponding to the transverse coupling.
Property Hscatter
The matrix of the Hamiltonian.
A class responsible for the Peierls and gauge transformations.
Property GaugeTransformationApplied
A logical value. True if a gauge transformation was applied on the Hamiltonians, or false otherwise.
Property HamiltoniansDecimated
A logical value. True if the Hamiltonian was decimated, or false otherwise.
function gauge_field(x, y, eta_B, Aconst, height, lattice_constant)
Scalar gauge field connecting Landaux and Landauy gauges.
Property fazis_mtx_scatter_t
The matrix of the Peierls phases for the transverse coupling.
Structure containing the coordinates and other quantum number identifiers of the sites in the Hamilto...
function Read(MemberName)
Query for the value of an attribute in the class.
function structures(name)
A class to create and store Hamiltonian of the scattering region.