<SYSTEM_TASK:>
Given the following text description, write Python code to implement the functionality described below step by step
<END_TASK>
<USER_TASK:>
Description:
 A simple method for segmenting rectilinear crop plots
The following outlines the method in https
Step1:  Read in a test image subset. Replace with your own if required parameters will need to be adjusted, needless to say complete segmentation is not guaranteed - will be dependent upon your image.
Step2:  The classical Canny edge detection.
Experimental GUI below, we follow Canny's original rule of thumb with the low threshold being divided by 2. 
From this we can derive the parameters for the crop segmentation.
Step3:  Phase congruency edge detection
See https
Step4:  Segment the plots
The function houghseg segments the plots. In this case, phase congruency is 'cleaner' edge detector, so it is used.
We are interested in the larger rectangular plots here so we use the min_area param to constrain this.
<ASSISTANT_TASK:>
Python Code:
%matplotlib inline
import cv2
from geospatial_learn import raster
from geospatial_learn.utilities import do_phasecong, houghseg
from math import ceil 
import matplotlib.pyplot as plt
from skimage.color import rgb2gray, label2rgb
from skimage.feature import canny
from skimage.exposure import rescale_intensity
Explanation: A simple method for segmenting rectilinear crop plots
The following outlines the method in https://www.frontiersin.org/articles/10.3389/fpls.2020.591886/full employing simple image processing techniques to extract crop plots. This is easily implemented using scikit-image or open cv, but available as a functionality within this library. 
The method employs edge detection, hough line detection then segment reduction to arrive at the plots of interest. The merit is the simplicity, though it is somewhat inflexible being limited to rectilinear plots. 
Needless to say complete segmentation is not guaranteed - will be dependent upon your image.
End of explanation
inRas = 'figures/weetestorig.tif'
img = raster.raster2array(inRas, bands=[1,2,3])
# for testing below
gray =  rgb2gray(img)
plt.imshow(img)
plt.show()
Explanation: Read in a test image subset. Replace with your own if required parameters will need to be adjusted, needless to say complete segmentation is not guaranteed - will be dependent upon your image.
End of explanation
def icanny(high_threshold, *args, **kwargs): #...do it
    
    inIm = gray#.astype(np.float)
 
    low_threshold = high_threshold / 2
    edge = canny(inIm, low_threshold=low_threshold,  high_threshold=high_threshold, *args, **kwargs)
    
    # Comment the first 2 lines if you want more space
    plt.figure(figsize=(15,15))
    plt.subplot(121)
    plt.imshow(img)
    plt.subplot(122)
    plt.imshow(edge)
    plt.show()
    
#    return edge
    
    
from ipywidgets import widgets
cTester = widgets.interact(icanny,
                           #k=widgets.IntSlider(min=3, max=100, step=2, continuous_update=False),
                              sigma=widgets.IntSlider(min=0, max=100, step=1, continuous_update=False),
                              #low_threshold=widgets.IntSlider(min=0, max=255, step=1, continuous_update=False),
                              high_threshold=widgets.FloatSlider(min=0, max=1, step=0.01, continuous_update=False))
Explanation: The classical Canny edge detection.
Experimental GUI below, we follow Canny's original rule of thumb with the low threshold being divided by 2. 
From this we can derive the parameters for the crop segmentation.
End of explanation
def iphase(*args, **kwargs):
    
    plt.figure(figsize=(15,15))
    plt.subplot(121)
    plt.imshow(img)
    plt.subplot(122)
    edge = do_phasecong(gray, *args, **kwargs)
    plt.imshow(edge)
    plt.show()
    
    
from ipywidgets import widgets
cTester = widgets.interact(iphase,
                           sigma=widgets.IntSlider(min=0, max=50, step=1, continuous_update=False),
                              low_t=widgets.IntSlider(min=0, max=256, step=1, continuous_update=False),
                              hi_t=widgets.IntSlider(min=0, max=256, step=1, continuous_update=False))
Explanation: Phase congruency edge detection
See https://link.springer.com/article/10.1007/s004260000024
An alternative method for edges, which may or may not prove more useful  albeit at a reduced speed with the python version ustilised here.
End of explanation
outShp = 'mytest.shp'
segments = houghseg(inRas, outShp, edge='phase', sigma=4, min_area=4)
plt.figure(figsize=(15,15))
plt.subplot(121)
plt.imshow(img)
plt.subplot(122)
plt.imshow(segments, cmap='gray')
Explanation: Segment the plots
The function houghseg segments the plots. In this case, phase congruency is 'cleaner' edge detector, so it is used.
We are interested in the larger rectangular plots here so we use the min_area param to constrain this.
End of explanation
<END_TASK>